ECC Digital Signature

package main

import (
	"crypto/ecdsa"
	"crypto/elliptic"
	"crypto/rand"
	"crypto/x509"
	"os"
	"encoding/pem"
	"crypto/sha256"
	"math/big"
	"fmt"
)

func ECCGenKey(privatePath string,publicPath string) error {
	privateKey,err:=ecdsa.GenerateKey(elliptic.P521(),rand.Reader)
	if err!=nil {
		return err
	}

	privateStream,err:=x509.MarshalECPrivateKey(privateKey)
	if err!=nil {
		return err
	}

	privateFile,err:=os.Create(privatePath)
	if err!=nil {
		return err
	}
	defer privateFile.Close()

	err=pem.Encode(privateFile,&pem.Block{
		Type:"ecdsa private key",
		Bytes:privateStream,
	})
	if err!=nil {
		return err
	}

	publicKey:=privateKey.PublicKey

	publicStream,err:=x509.MarshalPKIXPublicKey(&publicKey)
	if err!=nil {
		return err
	}

	publicFile,err:=os.Create(publicPath)
	if err!=nil {
		return err
	}
	defer publicFile.Close()

	err=pem.Encode(publicFile,&pem.Block{
		Type:"ecdsa public key",
		Bytes:publicStream,
	})
	if err!=nil {
		return err
	}

	return nil
}

func Sign(src []byte,privatePath string) ([]byte,[]byte,error) {
	privateFile,err:=os.Open(privatePath)
	if err!=nil {
		return nil,nil,err
	}
	defer privateFile.Close()

	fileinfo,err:=os.Stat(privatePath)
	if err!=nil {
		return nil,nil,err
	}

	m:=make([]byte,fileinfo.Size())
	privateFile.Read(m)

	block,_:=pem.Decode(m)

	privateKey,err:=x509.ParseECPrivateKey(block.Bytes)
	if err!=nil {
		return nil,nil,err
	}

	h:=sha256.Sum256(src)
	s,r,err:=ecdsa.Sign(rand.Reader,privateKey,h[:])
	sb,err:=s.MarshalText()
	if err!=nil {
		return nil,nil,err
	}
	rb,err:=r.MarshalText()
	if err!=nil {
		return nil,nil,err
	}

	return sb,rb,nil
}

func Verify(src []byte,publicPath string,sb []byte,rb []byte) (bool,error) {
	publicFile,err:=os.Open(publicPath)
	if err!=nil {
		return false, err
	}
	defer publicFile.Close()

	fileinfo,err:=os.Stat(publicPath)
	if err!=nil {
		return false, err
	}

	m:=make([]byte,fileinfo.Size())
	publicFile.Read(m)

	block,_:=pem.Decode(m)

	publicKey,err:=x509.ParsePKIXPublicKey(block.Bytes)
	if err!=nil {
		return false, err
	}

	var s,r big.Int
	err=s.UnmarshalText(sb)
	if err!=nil {
		return false, err
	}
	err=r.UnmarshalText(rb)
	if err!=nil {
		return false, err
	}

	/*xb:=publicKey.(*ecdsa.PublicKey).X.Bytes()
	yb:=publicKey.(*ecdsa.PublicKey).Y.Bytes()
	b:=append(xb,yb...)

	var x,y big.Int
	n:=len(b)
	x.SetBytes(b[:n/2])
	y.SetBytes(b[n/2:])
	rawPublicKey:=ecdsa.PublicKey{elliptic.P521(),&x,&y}*/

	h:=sha256.Sum256(src)
	return ecdsa.Verify(publicKey.(*ecdsa.PublicKey),h[:],&s,&r),nil
	//return ecdsa.Verify(&rawPublicKey,h[:],&s,&r),nil
}

func main()  {
	privatePath:="private181122.pem"
	publicPath:="public181122.pem"
	err:=ECCGenKey(privatePath,publicPath)
	if err!=nil {
		fmt.Print(err)
		return
	}

	s,r,err:=Sign([]byte("waist-length hair"),privatePath)
	if err!=nil {
		fmt.Print(err)
		return
	}

	x,err:=Verify([]byte("waist-length hair"),publicPath,s,r)
	if err!=nil {
		fmt.Print(err)
		return
	}
	fmt.Print(x)

	y,err:=Verify([]byte("central parting waist-length hair"),publicPath,s,r)
	if err!=nil {
		fmt.Print(err)
		return
	}
	fmt.Print(y)
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值