GO

2013-12-18 18 views
5

'da RSA-SHA ile imzalama ve kod çözme Bir dizeyi imzalamaya çalışıyorum ve daha sonra bunu ortak anahtarla doğrulayın. Doğrulanmış sonucum boş. Neyi yanlış yapıyorum?GO

package main 

import (
    "crypto" 
    "crypto/rand" 
    "crypto/rsa" 
    "crypto/sha256" 
    "crypto/x509" 
    "encoding/base64" 
    "encoding/pem" 
    "errors" 
    "fmt" 
    "io/ioutil" 
) 

func main() { 
    signer, err := loadPrivateKey("private.pem"); 
    if err != nil { 
     fmt.Errorf("signer is damaged: %v", err) 
    } 

    toSign := "date: Thu, 05 Jan 2012 21:31:40 GMT"; 

    signed, err := signer.Sign([]byte(toSign)) 
    if err != nil { 
     fmt.Errorf("could not sign request: %v", err) 
    } 
    sig := base64.StdEncoding.EncodeToString(signed) 
    fmt.Printf("Encoded: %v\n", sig) 


    parser, perr := loadPublicKey("public.pem"); 
    if perr != nil { 
     fmt.Errorf("could not sign request: %v", err) 
    } 
    unsigned, err := parser.Unsign(signed); 
    if err != nil { 
     fmt.Errorf("could not sign request: %v", err) 
    } 

    fmt.Printf("Decrypted: %v\n", base64.StdEncoding.EncodeToString(unsigned))  
} 


// loadPrivateKey loads an parses a PEM encoded private key file. 
func loadPublicKey(path string) (Unsigner, error) { 
     data, err := ioutil.ReadFile(path) 

     if err != nil { 
       return nil, err 
     } 
     return parsePublicKey(data) 
} 

// parsePublicKey parses a PEM encoded private key. 
func parsePublicKey(pemBytes []byte) (Unsigner, error) { 
     block, _ := pem.Decode(pemBytes) 
     if block == nil { 
       return nil, errors.New("ssh: no key found") 
     } 

     var rawkey interface{} 
     switch block.Type { 
     case "PUBLIC KEY": 
       rsa, err := x509.ParsePKIXPublicKey(block.Bytes) 
       if err != nil { 
         return nil, err 
       } 
       rawkey = rsa 
     default: 
       return nil, fmt.Errorf("ssh: unsupported key type %q", block.Type) 
     } 

     return newUnsignerFromKey(rawkey) 
} 


// loadPrivateKey loads an parses a PEM encoded private key file. 
func loadPrivateKey(path string) (Signer, error) { 
     data, err := ioutil.ReadFile(path) 
     if err != nil { 
       return nil, err 
     } 
     return parsePrivateKey(data) 
} 

// parsePublicKey parses a PEM encoded private key. 
func parsePrivateKey(pemBytes []byte) (Signer, error) { 
     block, _ := pem.Decode(pemBytes) 
     if block == nil { 
       return nil, errors.New("ssh: no key found") 
     } 

     var rawkey interface{} 
     switch block.Type { 
     case "RSA PRIVATE KEY": 
       rsa, err := x509.ParsePKCS1PrivateKey(block.Bytes) 
       if err != nil { 
         return nil, err 
       } 
       rawkey = rsa 
     default: 
       return nil, fmt.Errorf("ssh: unsupported key type %q", block.Type) 
     } 
     return newSignerFromKey(rawkey) 
} 

// A Signer is can create signatures that verify against a public key. 
type Signer interface { 
     // Sign returns raw signature for the given data. This method 
     // will apply the hash specified for the keytype to the data. 
     Sign(data []byte) ([]byte, error) 
} 

// A Signer is can create signatures that verify against a public key. 
type Unsigner interface { 
     // Sign returns raw signature for the given data. This method 
     // will apply the hash specified for the keytype to the data. 
     Unsign(data []byte) ([]byte, error) 
} 

func newSignerFromKey(k interface{}) (Signer, error) { 
     var sshKey Signer 
     switch t := k.(type) { 
     case *rsa.PrivateKey: 
       sshKey = &rsaPrivateKey{t} 
     default: 
       return nil, fmt.Errorf("ssh: unsupported key type %T", k) 
     } 
     return sshKey, nil 
} 

func newUnsignerFromKey(k interface{}) (Unsigner, error) { 
     var sshKey Unsigner 
     switch t := k.(type) { 
     case *rsa.PublicKey: 
       sshKey = &rsaPublicKey{t} 
     default: 
       return nil, fmt.Errorf("ssh: unsupported key type %T", k) 
     } 
     return sshKey, nil 
} 

type rsaPublicKey struct { 
    *rsa.PublicKey 
} 

type rsaPrivateKey struct { 
     *rsa.PrivateKey 
} 

// Sign signs data with rsa-sha256 
func (r *rsaPrivateKey) Sign(data []byte) ([]byte, error) { 
     h := sha256.New() 
     h.Write(data) 
     d := h.Sum(nil) 
     return rsa.SignPKCS1v15(rand.Reader, r.PrivateKey, crypto.SHA256, d) 
} 

// Unsign encrypts data with rsa-sha256 
func (r *rsaPublicKey) Unsign(message []byte) ([]byte, error) { 
     return rsa.EncryptPKCS1v15(rand.Reader, r.PublicKey, message)   
} 

private.pem şuna benzer:

-----BEGIN RSA PRIVATE KEY----- 
MIICXgIBAAKBgQDCFENGw33yGihy92pDjZQhl0C36rPJj+CvfSC8+q28hxA161QF 
NUd13wuCTUcq0Qd2qsBe/2hFyc2DCJJg0h1L78+6Z4UMR7EOcpfdUE9Hf3m/hs+F 
UR45uBJeDK1HSFHD8bHKD6kv8FPGfJTotc+2xjJwoYi+1hqp1fIekaxsyQIDAQAB 
AoGBAJR8ZkCUvx5kzv+utdl7T5MnordT1TvoXXJGXK7ZZ+UuvMNUCdN2QPc4sBiA 
QWvLw1cSKt5DsKZ8UETpYPy8pPYnnDEz2dDYiaew9+xEpubyeW2oH4Zx71wqBtOK 
kqwrXa/pzdpiucRRjk6vE6YY7EBBs/g7uanVpGibOVAEsqH1AkEA7DkjVH28WDUg 
f1nqvfn2Kj6CT7nIcE3jGJsZZ7zlZmBmHFDONMLUrXR/Zm3pR5m0tCmBqa5RK95u 
412jt1dPIwJBANJT3v8pnkth48bQo/fKel6uEYyboRtA5/uHuHkZ6FQF7OUkGogc 
mSJluOdc5t6hI1VsLn0QZEjQZMEOWr+wKSMCQQCC4kXJEsHAve77oP6HtG/IiEn7 
kpyUXRNvFsDE0czpJJBvL/aRFUJxuRK91jhjC68sA7NsKMGg5OXb5I5Jj36xAkEA 
gIT7aFOYBFwGgQAQkWNKLvySgKbAZRTeLBacpHMuQdl1DfdntvAyqpAZ0lY0RKmW 
G6aFKaqQfOXKCyWoUiVknQJAXrlgySFci/2ueKlIE1QqIiLSZ8V8OlpFLRnb1pzI 
7U1yQXnTAEFYM560yJlzUpOb1V4cScGd365tiSMvxLOvTA== 
-----END RSA PRIVATE KEY----- 

Ve public.pem:

-----BEGIN PUBLIC KEY----- 
MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDCFENGw33yGihy92pDjZQhl0C3 
6rPJj+CvfSC8+q28hxA161QFNUd13wuCTUcq0Qd2qsBe/2hFyc2DCJJg0h1L78+6 
Z4UMR7EOcpfdUE9Hf3m/hs+FUR45uBJeDK1HSFHD8bHKD6kv8FPGfJTotc+2xjJw 
oYi+1hqp1fIekaxsyQIDAQAB 
-----END PUBLIC KEY----- 

teşekkürler.

+0

Biraz kafam karıştı. Encode ve sonra Decode veya imza imzalamak ve imzalamak istiyor musunuz? (Kripto terminolojisiyle çok fazla kullanmıyorum) – ANisus

+0

İmzayı imzalamak ve imzalamak istiyorum. Güncelleme açıklaması. –

+0

Dikkat edin - popüler inancın aksine - RSA şifreleme/şifre çözme, bir karma ile RSA imzalama/doğrulamadan farklıdır. En azından, farklı bir dolgu mekanizması kullanır. –

cevap

6

Kodunuzdaki sorun, orijinal iletiyi doğrulamak için Unsign yerine imzayı kodunun girmeye çalışmasıdır.

Arayüzüne ve Unsign yapılan değişiklikleri olmalı gerekir: http://play.golang.org/p/bzpD7Pa9mr

Bazı modifikasyonlar da ioutils önlemek için yapılmıştır:

İşte
// Unsign verifies the message using a rsa-sha256 signature 
func (r *rsaPublicKey) Unsign(message []byte, sig []byte) error { 
    h := sha256.New() 
    h.Write(message) 
    d := h.Sum(nil) 
    return rsa.VerifyPKCS1v15(r.PublicKey, crypto.SHA256, d, sig) 
} 

doğrulama bir oyun örneğidir.

+0

playgroud çalışamaz. –

+0

@buzz: Hmm, oyun alanım bağlantısına tıkladıktan sonra Run'a bastım. İyi çalıştı. Oyun alanı kodunu yerel olarak mı deniyorsunuz? – ANisus

+0

oh üzgünüm, benim hatam. Bir hata yaptım. –