main
Raw Download raw file
 1package brainpool
 2
 3import (
 4	"crypto/elliptic"
 5	"math/big"
 6)
 7
 8var _ elliptic.Curve = (*rcurve)(nil)
 9
10type rcurve struct {
11	twisted elliptic.Curve
12	params  *elliptic.CurveParams
13	z       *big.Int
14	zinv    *big.Int
15	z2      *big.Int
16	z3      *big.Int
17	zinv2   *big.Int
18	zinv3   *big.Int
19}
20
21var (
22	two   = big.NewInt(2)
23	three = big.NewInt(3)
24)
25
26func newrcurve(twisted elliptic.Curve, params *elliptic.CurveParams, z *big.Int) *rcurve {
27	zinv := new(big.Int).ModInverse(z, params.P)
28	return &rcurve{
29		twisted: twisted,
30		params:  params,
31		z:       z,
32		zinv:    zinv,
33		z2:      new(big.Int).Exp(z, two, params.P),
34		z3:      new(big.Int).Exp(z, three, params.P),
35		zinv2:   new(big.Int).Exp(zinv, two, params.P),
36		zinv3:   new(big.Int).Exp(zinv, three, params.P),
37	}
38}
39
40func (curve *rcurve) toTwisted(x, y *big.Int) (*big.Int, *big.Int) {
41	var tx, ty big.Int
42	tx.Mul(x, curve.z2)
43	tx.Mod(&tx, curve.params.P)
44	ty.Mul(y, curve.z3)
45	ty.Mod(&ty, curve.params.P)
46	return &tx, &ty
47}
48
49func (curve *rcurve) fromTwisted(tx, ty *big.Int) (*big.Int, *big.Int) {
50	var x, y big.Int
51	x.Mul(tx, curve.zinv2)
52	x.Mod(&x, curve.params.P)
53	y.Mul(ty, curve.zinv3)
54	y.Mod(&y, curve.params.P)
55	return &x, &y
56}
57
58func (curve *rcurve) Params() *elliptic.CurveParams {
59	return curve.params
60}
61
62func (curve *rcurve) IsOnCurve(x, y *big.Int) bool {
63	return curve.twisted.IsOnCurve(curve.toTwisted(x, y))
64}
65
66func (curve *rcurve) Add(x1, y1, x2, y2 *big.Int) (x, y *big.Int) {
67	tx1, ty1 := curve.toTwisted(x1, y1)
68	tx2, ty2 := curve.toTwisted(x2, y2)
69	return curve.fromTwisted(curve.twisted.Add(tx1, ty1, tx2, ty2))
70}
71
72func (curve *rcurve) Double(x1, y1 *big.Int) (x, y *big.Int) {
73	return curve.fromTwisted(curve.twisted.Double(curve.toTwisted(x1, y1)))
74}
75
76func (curve *rcurve) ScalarMult(x1, y1 *big.Int, scalar []byte) (x, y *big.Int) {
77	tx1, ty1 := curve.toTwisted(x1, y1)
78	return curve.fromTwisted(curve.twisted.ScalarMult(tx1, ty1, scalar))
79}
80
81func (curve *rcurve) ScalarBaseMult(scalar []byte) (x, y *big.Int) {
82	return curve.fromTwisted(curve.twisted.ScalarBaseMult(scalar))
83}