arnaucube
arnaucube/cryptofunPublic Self-hosted repository
cryptofun/rsa/rsa.go
rsa/rsa.goRaw
  1package rsa
  2
  3import (
  4	"bytes"
  5	"crypto/rand"
  6	"math/big"
  7)
  8
  9const (
 10	bits = 512 // 2048
 11)
 12
 13var bigOne = big.NewInt(int64(1))
 14
 15type PublicKey struct {
 16	E *big.Int `json:"e"`
 17	N *big.Int `json:"n"`
 18}
 19type PublicKeyString struct {
 20	E string `json:"e"`
 21	N string `json:"n"`
 22}
 23type PrivateKey struct {
 24	D *big.Int `json:"d"`
 25	N *big.Int `json:"n"`
 26}
 27
 28type Key struct {
 29	PubK  PublicKey
 30	PrivK PrivateKey
 31}
 32
 33func GenerateKeyPair() (key Key, err error) {
 34	p, err := rand.Prime(rand.Reader, bits/2)
 35	if err != nil {
 36		return key, err
 37	}
 38	q, err := rand.Prime(rand.Reader, bits/2)
 39	if err != nil {
 40		return key, err
 41	}
 42
 43	n := new(big.Int).Mul(p, q)
 44	p_1 := new(big.Int).Sub(p, bigOne)
 45	q_1 := new(big.Int).Sub(q, bigOne)
 46	phi := new(big.Int).Mul(p_1, q_1)
 47	e := 65537
 48	var pubK PublicKey
 49	pubK.E = big.NewInt(int64(e))
 50	pubK.N = n
 51
 52	d := new(big.Int).ModInverse(big.NewInt(int64(e)), phi)
 53
 54	var privK PrivateKey
 55	privK.D = d
 56	privK.N = n
 57
 58	key.PubK = pubK
 59	key.PrivK = privK
 60	return key, nil
 61}
 62
 63func Encrypt(m *big.Int, pubK PublicKey) *big.Int {
 64	c := new(big.Int).Exp(m, pubK.E, pubK.N)
 65	return c
 66}
 67func Decrypt(c *big.Int, privK PrivateKey) *big.Int {
 68	m := new(big.Int).Exp(c, privK.D, privK.N)
 69	return m
 70}
 71
 72func Blind(m *big.Int, r *big.Int, pubK PublicKey) *big.Int {
 73	rE := new(big.Int).Exp(r, pubK.E, nil)
 74	mrE := new(big.Int).Mul(m, rE)
 75	mBlinded := new(big.Int).Mod(mrE, pubK.N)
 76	return mBlinded
 77}
 78
 79func BlindSign(m *big.Int, privK PrivateKey) *big.Int {
 80	sigma := new(big.Int).Exp(m, privK.D, privK.N)
 81	return sigma
 82}
 83func Unblind(sigma *big.Int, r *big.Int, pubK PublicKey) *big.Int {
 84	r1 := new(big.Int).ModInverse(r, pubK.N)
 85	bsr := new(big.Int).Mul(sigma, r1)
 86	sig := new(big.Int).Mod(bsr, pubK.N)
 87	return sig
 88}
 89func Verify(msg *big.Int, mSigned *big.Int, pubK PublicKey) bool {
 90	//decrypt the mSigned with pubK
 91	Cd := new(big.Int).Exp(mSigned, pubK.E, nil)
 92	m := new(big.Int).Mod(Cd, pubK.N)
 93	return bytes.Equal(msg.Bytes(), m.Bytes())
 94}
 95
 96func HomomorphicMul(c1 *big.Int, c2 *big.Int, pubK PublicKey) *big.Int {
 97	c1c2 := new(big.Int).Mul(c1, c2)
 98	n2 := new(big.Int).Mul(pubK.N, pubK.N)
 99	d := new(big.Int).Mod(c1c2, n2)
100	return d
101}