GolangでのRSAの使用


GolangでのRSAの使用
一.RSAとは
ネット通信と頻繁に付き合うプログラム猿にとって、RSAという3つのアルファベットはきっと見慣れていないに違いない.RSAは非対称暗号化アルゴリズムであり,公開鍵暗号化や電子商取引で広く用いられている.RSAの核心は非対称暗号化アルゴリズムである.非対称暗号化には、鍵ペアのペアを生成する必要があります.1つは公開用の公開鍵(publickey)であり、もう1つは、漏洩できないプライベート鍵(privatekey)をプライベートで保存する必要がある.いずれかの鍵を使用して暗号化された情報は、別の鍵で復号してこそ復元されます.この特性を利用して、通常は2つの運用方式がある:1公開鍵暗号化、秘密鍵復号化--情報の暗号化、情報の漏洩防止②秘密鍵暗号化、公開鍵復号化--デジタル署名、認証
二.鍵ペアの生成
GenerateKey法によりPrivateKeyを生成できます
rsa.GenerateKey(random io.Reader, bits int) (*rsa.PrivateKey, error)

PrivateKeyの構造を見てみましょう
// A PrivateKey represents an RSA key
type PrivateKey struct {
     
	PublicKey            // public part.
	D         *big.Int   // private exponent
	Primes    []*big.Int // prime factors of N, has >= 2 elements.

	// Precomputed contains precomputed values that speed up private
	// operations, if available.
	Precomputed PrecomputedValues
}

PrivateKeyにPublicKeyが組み込まれている情報がわかります
// A PublicKey represents the public part of an RSA key.
type PublicKey struct {
     
	N *big.Int // modulus
	E int      // public exponent
}

もちろんopensslで鍵ペアのファイルを生成することもできます
openssl genrsa 1024 > private-key.pem  // 1024      (  bit)
openssl rsa -in private-key.pem -pubout -out public-key.pem

pemファイルから鍵を読み出す処理は以下の通りです.
func RSAReadPraviteKey(filePath string) (*rsa.PrivateKey, error) {
     
	privateKeyData, err := ioutil.ReadFile(filePath)
	if err != nil {
     
		return nil, err
	}

	privateKeyBlock, _ := pem.Decode(privateKeyData)
	var pri *rsa.PrivateKey
	pri, parseErr := x509.ParsePKCS1PrivateKey(privateKeyBlock.Bytes)
	if parseErr != nil {
     
		return nil, parseErr
	}

	return pri, nil
}
BEGIN RSA PRIVATE KEYから始まるファイル(PKCS#1)、x509.ParsePKCS1PrivateKeyからBEGIN PRIVATE KEYから始まるファイル(PKCS#8)、x509.ParsePKCS8PrivateKey
PublicKeyの処理は同様であり,利用方法はx509.ParsePKIXPublicKeyである.
三.暗号化
func EncryptOAEP(hash hash.Hash, random io.Reader, pub *PublicKey, msg []byte, label []byte) ([]byte, error)
func Encrypt(msg []byte, public *rsa.PublicKey) []byte {
     
  // crypto/rand.Reader is a good source of entropy for randomizing the
  // encryption function.
  rng := rand.Reader

  ciphertext, err := EncryptOAEP(sha256.New(), rng, public, msg, nil)
  if err != nil {
     
      fmt.Fprintf(os.Stderr, "Error from encryption: %s
"
, err) return } return ciphertext }

四.解読
func DecryptOAEP(hash hash.Hash, random io.Reader, priv *PrivateKey, ciphertext []byte, label []byte) ([]byte, error)
func Decrypt(ciphertext []byte, private *rsa.PrivateKey) []byte {
     
  // crypto/rand.Reader is a good source of entropy for randomizing the
  // encryption function.
  rng := rand.Reader

  plaintext, err := DecryptOAEP(sha256.New(), rng, private, ciphertext, nil)
  if err != nil {
     
      fmt.Fprintf(os.Stderr, "Error from decryption: %s
"
, err) return } return plaintext }

注:暗号化と復号化で使用するhashメソッドは一致する必要があります.
五.関連名詞
x.509:X.509はITU-T標準化部門が以前のASN.1に基づいて定義した証明書標準のセットである.X.509証明書はTLS/SSLを含む多くのネットワークプロトコルに適用されていると同時に、電子署名サービスなどの多くの非オンラインアプリケーションシーンにも使用されています.X.509証明書には、公開鍵、アイデンティティ情報(例えば、ネットワークホスト名、組織名または個人名など)と署名情報(証明書発行機関CAの署名であってもよいし、自己署名であってもよい)が含まれている.信頼できる証明書発行機関を介して署名したり、他の方法で検証したりできる証明書については、証明書の所有者は、証明書と対応する秘密鍵で安全な通信を作成し、ドキュメントにデジタル署名することができます.
ASN.1:ASN.1(Abstract Syntax Notation One)は、データの表現、符号化、伝送、復号を記述するための柔軟な表記の標準である.特定のコンピュータハードウェアとは独立したオブジェクト構造を記述するための正式で曖昧で正確な規則を提供する.
PKCS:The Public-Key Cryptography Standards(PKCS)は、証明書の申請、証明書の更新、証明書の廃棄表の発行、証明書の内容の拡張、デジタル署名、デジタル封筒のフォーマットなど、米国RSAデータセキュリティ会社とそのパートナーが制定した公開鍵暗号学基準のセットである.
OAEP:最適非対称暗号化パディング.RSA暗号化でよく用いられるパディングモードは、RSA_PKCS 1_PADDING、RSA_PKCS 1_OAEP_PADDING、RSA_NO_PADDINGの3種類がある.RSA暗号化される明文の長さは、RSAパディングモードによって制限されるが、RSAが暗号化されるたびにブロック長はkey lengthである.
PKIX:X.509標準をインターネットに応用するため、X.509標準に基づくPKIシステムを建設するため、IETF(Internet Engineering Task Force)は1995年にPKIXワークグループを設立し、インターネットに関連するPKI標準の制定を開始した.