/// <summary> /// 从(消息,签名)恢复公钥 /// </summary> /// <param name="message"></param> /// <param name="signature"></param> /// <returns></returns> unsafe public static PublicKey RecoverPublicKey(ReadOnlySpan <byte> message, Signature signature) { if (message.Length != 32) { throw new InvalidMessageException("消息长度必须是32字节"); } U256N s = signature.S; var m = new U256N(message); var rY = EllipticCurve.GetY(signature.R); if (rY.Value.v0 % 2 != 0) { s = -s; } var rP = new JacobianPoint(signature.R, rY); var r_inv = ~new U256N(signature.R); var u1 = EllipticCurve.MulG(-m * r_inv); var u2 = s * r_inv; var p = (Point)(rP * u2 + u1); return(new PublicKey(p.X, p.Y)); }