mirror of
				https://github.com/go-gitea/gitea
				synced 2025-10-27 17:38:25 +00:00 
			
		
		
		
	* Switch to keybase go-crypto (for some elliptic curve key) + test
* Use assert.NoError 
and add a little more context to failing test description
* Use assert.(No)Error everywhere 🌈
and assert.Error in place of .Nil/.NotNil
		
	
		
			
				
	
	
		
			114 lines
		
	
	
		
			3.0 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
			
		
		
	
	
			114 lines
		
	
	
		
			3.0 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
| package curve25519
 | |
| 
 | |
| import (
 | |
| 	"crypto/elliptic"
 | |
| 	"math/big"
 | |
| 	"sync"
 | |
| )
 | |
| 
 | |
| var cv25519 cv25519Curve
 | |
| 
 | |
| type cv25519Curve struct {
 | |
| 	*elliptic.CurveParams
 | |
| }
 | |
| 
 | |
| func copyReverse(dst []byte, src []byte) {
 | |
| 	// Curve 25519 multiplication functions expect scalars in reverse
 | |
| 	// order than PGP. To keep the curve25519Curve type consistent
 | |
| 	// with other curves, we reverse it here.
 | |
| 	for i, j := 0, len(src)-1; j >= 0; i, j = i+1, j-1 {
 | |
| 		dst[i] = src[j]
 | |
| 	}
 | |
| }
 | |
| 
 | |
| func (cv25519Curve) ScalarMult(x1, y1 *big.Int, scalar []byte) (x, y *big.Int) {
 | |
| 	// Assume y1 is 0 with cv25519.
 | |
| 	var dst [32]byte
 | |
| 	var x1Bytes [32]byte
 | |
| 	var scalarBytes [32]byte
 | |
| 
 | |
| 	copy(x1Bytes[:], x1.Bytes()[:32])
 | |
| 	copyReverse(scalarBytes[:], scalar[:32])
 | |
| 
 | |
| 	scalarMult(&dst, &scalarBytes, &x1Bytes)
 | |
| 
 | |
| 	x = new(big.Int).SetBytes(dst[:])
 | |
| 	y = new(big.Int)
 | |
| 	return x, y
 | |
| }
 | |
| 
 | |
| func (cv25519Curve) ScalarBaseMult(scalar []byte) (x, y *big.Int) {
 | |
| 	var dst [32]byte
 | |
| 	var scalarBytes [32]byte
 | |
| 	copyReverse(scalarBytes[:], scalar[:32])
 | |
| 	scalarMult(&dst, &scalarBytes, &basePoint)
 | |
| 	x = new(big.Int).SetBytes(dst[:])
 | |
| 	y = new(big.Int)
 | |
| 	return x, y
 | |
| }
 | |
| 
 | |
| func (cv25519Curve) IsOnCurve(bigX, bigY *big.Int) bool {
 | |
| 	return bigY.Sign() == 0 // bigY == 0 ?
 | |
| }
 | |
| 
 | |
| // More information about 0x40 point format:
 | |
| // https://tools.ietf.org/html/draft-koch-eddsa-for-openpgp-00#section-3
 | |
| // In addition to uncompressed point format described here:
 | |
| // https://tools.ietf.org/html/rfc6637#section-6
 | |
| 
 | |
| func (cv25519Curve) MarshalType40(x, y *big.Int) []byte {
 | |
| 	byteLen := 32
 | |
| 
 | |
| 	ret := make([]byte, 1+byteLen)
 | |
| 	ret[0] = 0x40
 | |
| 
 | |
| 	xBytes := x.Bytes()
 | |
| 	copy(ret[1+byteLen-len(xBytes):], xBytes)
 | |
| 	return ret
 | |
| }
 | |
| 
 | |
| func (cv25519Curve) UnmarshalType40(data []byte) (x, y *big.Int) {
 | |
| 	if len(data) != 1+32 {
 | |
| 		return nil, nil
 | |
| 	}
 | |
| 	if data[0] != 0x40 {
 | |
| 		return nil, nil
 | |
| 	}
 | |
| 	x = new(big.Int).SetBytes(data[1:])
 | |
| 	// Any x is a valid curve point.
 | |
| 	return x, new(big.Int)
 | |
| }
 | |
| 
 | |
| // ToCurve25519 casts given elliptic.Curve type to Curve25519 type, or
 | |
| // returns nil, false if cast was unsuccessful.
 | |
| func ToCurve25519(cv elliptic.Curve) (cv25519Curve, bool) {
 | |
| 	cv2, ok := cv.(cv25519Curve)
 | |
| 	return cv2, ok
 | |
| }
 | |
| 
 | |
| func initCv25519() {
 | |
| 	cv25519.CurveParams = &elliptic.CurveParams{Name: "Curve 25519"}
 | |
| 	// Some code relies on these parameters being available for
 | |
| 	// checking Curve coordinate length. They should not be used
 | |
| 	// directly for any calculations.
 | |
| 	cv25519.P, _ = new (big.Int).SetString("7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffed", 16)
 | |
| 	cv25519.N, _ = new (big.Int).SetString("1000000000000000000000000000000014def9dea2f79cd65812631a5cf5d3ed", 16)
 | |
| 	cv25519.Gx, _ = new (big.Int).SetString("9", 16)
 | |
| 	cv25519.Gy, _ = new (big.Int).SetString("20ae19a1b8a086b4e01edd2c7748d14c923d4d7e6d7c61b229e9c5a27eced3d9", 16)
 | |
| 	cv25519.BitSize = 256
 | |
| }
 | |
| 
 | |
| var initonce sync.Once
 | |
| 
 | |
| // Cv25519 returns a Curve which (partially) implements Cv25519. Only
 | |
| // ScalarMult and ScalarBaseMult are valid for this curve. Add and
 | |
| // Double should not be used.
 | |
| func Cv25519() elliptic.Curve {
 | |
| 	initonce.Do(initCv25519)
 | |
| 	return cv25519
 | |
| }
 | |
| 
 | |
| func (curve cv25519Curve) Params() *elliptic.CurveParams {
 | |
| 	return curve.CurveParams
 | |
| }
 |