def test_libsecp256k1() -> None: try: import btclib_libsecp256k1.ssa # pylint: disable=import-outside-toplevel except ImportError: # pragma: no cover pytest.skip() prvkey, X_Q = ssa.gen_keys(0x1) pubkey_bytes = X_Q.to_bytes(32, "big") msg = "Satoshi Nakamoto".encode() msg_hash = reduce_to_hlen(msg) libsecp256k1_sig = btclib_libsecp256k1.ssa.sign(msg_hash, prvkey) btclib_sig = ssa.sign_(msg_hash, prvkey) assert btclib_libsecp256k1.ssa.verify(msg_hash, pubkey_bytes, btclib_sig.serialize()) assert ssa.verify(msg, X_Q, libsecp256k1_sig)
dsa_valid = dsa.verify(msg, dsa_pub, dsa_sig) print("valid ECDSA sig:", dsa_valid) # ECSSA print("\n ECSSA") ssa_prv, ssa_pub = ssa.gen_keys() print("prv", hex(ssa_prv)) print("pub", hex(ssa_pub)) ssa_sig = ssa.sign(msg, ssa_prv) print("r:", hex(ssa_sig.r)) print("s:", hex(ssa_sig.s)) ssa_valid = ssa.verify(msg, ssa_pub, ssa_sig) print("valid ECSSA sig:", ssa_valid) # ECBMS print("\n ECBMS") bms_prv, bms_pub = bms.gen_keys() print("prv", bms_prv) print("pub", bms_pub) bms_sig = bms.sign(msg, bms_prv) print("rf:", hex(bms_sig.rf)) print("r:", hex(bms_sig.dsa_sig.r)) print("s:", hex(bms_sig.dsa_sig.r)) bms_valid = bms.verify(msg, bms_pub, bms_sig)
def test_signature() -> None: msg = "Satoshi Nakamoto".encode() q, x_Q = ssa.gen_keys(0x01) sig = ssa.sign(msg, q) ssa.assert_as_valid(msg, x_Q, sig) assert ssa.verify(msg, x_Q, sig) assert sig == ssa.Sig.parse(sig.serialize()) assert sig == ssa.Sig.parse(sig.serialize().hex()) msg_fake = "Craig Wright".encode() assert not ssa.verify(msg_fake, x_Q, sig) err_msg = r"y_K is odd|signature verification failed" with pytest.raises(BTClibRuntimeError, match=err_msg): ssa.assert_as_valid(msg_fake, x_Q, sig) _, x_Q_fake = ssa.gen_keys(0x02) assert not ssa.verify(msg, x_Q_fake, sig) with pytest.raises(BTClibRuntimeError, match=err_msg): ssa.assert_as_valid(msg, x_Q_fake, sig) _, x_Q_fake = ssa.gen_keys(0x4) assert not ssa.verify(msg, x_Q_fake, sig) with pytest.raises(BTClibRuntimeError, match=err_msg): ssa.assert_as_valid(msg, x_Q_fake, sig) err_msg = "not a BIP340 public key" with pytest.raises(BTClibTypeError, match=err_msg): ssa.assert_as_valid(msg, INF, sig) # type: ignore with pytest.raises(BTClibTypeError, match=err_msg): ssa.point_from_bip340pub_key(INF) # type: ignore sig_invalid = ssa.Sig(sig.ec.p, sig.s, check_validity=False) assert not ssa.verify(msg, x_Q, sig_invalid) err_msg = "x-coordinate not in 0..p-1: " with pytest.raises(BTClibValueError, match=err_msg): ssa.assert_as_valid(msg, x_Q, sig_invalid) sig_invalid = ssa.Sig(sig.r, sig.ec.p, check_validity=False) assert not ssa.verify(msg, x_Q, sig_invalid) err_msg = "scalar s not in 0..n-1: " with pytest.raises(BTClibValueError, match=err_msg): ssa.assert_as_valid(msg, x_Q, sig_invalid) m_bytes = reduce_to_hlen(msg, hf) err_msg = "invalid size: 31 bytes instead of 32" with pytest.raises(BTClibValueError, match=err_msg): ssa.assert_as_valid_(m_bytes[:31], x_Q, sig) with pytest.raises(BTClibValueError, match=err_msg): ssa.sign_(m_bytes[:31], q) err_msg = "private key not in 1..n-1: " with pytest.raises(BTClibValueError, match=err_msg): ssa.sign(msg, 0) # ephemeral key not in 1..n-1 err_msg = "private key not in 1..n-1: " with pytest.raises(BTClibValueError, match=err_msg): ssa.sign_(m_bytes, q, 0) with pytest.raises(BTClibValueError, match=err_msg): ssa.sign_(m_bytes, q, sig.ec.n)
Q = mult(q, ec.G)[0] print(f"PubKey: {hex(Q).upper()}") print("\n1. Message to be signed") orig_msg = "Paolo is afraid of ephemeral random numbers" msg = sha256(orig_msg.encode()).digest() print(f" {msg.hex().upper()}") print("2. Sign message") sig = sign(msg, q) print(f" r: {hex(sig.r).upper()}") print(f" s: {hex(sig.s).upper()}") print("3. Verify signature") print(verify(msg, Q, sig)) print("\n** Malleated signature") sm = ec.n - sig.s print(f" r: {hex(sig.r).upper()}") print(f" sm: {hex(sm).upper()}") print("** Verify malleated signature") print(verify(msg, Q, Sig(sig.r, sm))) print("\n1. Another message to sign") orig_msg2 = "and Paolo is right to be afraid" msg2 = sha256(orig_msg2.encode()).digest() print(msg2.hex().upper()) print("2. Sign message")