+++ /dev/null
-diff -r 7ec969250bfc src/pkg/crypto/openpgp/packet/private_key.go
---- a/src/pkg/crypto/openpgp/packet/private_key.go Tue Dec 27 09:49:19 2011 -0500
-+++ b/src/pkg/crypto/openpgp/packet/private_key.go Sat Dec 31 02:32:45 2011 +0100
-@@ -28,7 +28,7 @@
- encryptedData []byte
- cipher CipherFunction
- s2k func(out, in []byte)
-- PrivateKey interface{} // An *rsa.PrivateKey.
-+ PrivateKey interface{} // An *rsa.PrivateKey or *dsa.PrivateKey.
- sha1Checksum bool
- iv []byte
- }
-@@ -40,6 +40,13 @@
- return pk
- }
-
-+func NewDSAPrivateKey(currentTime time.Time, priv *dsa.PrivateKey, isSubkey bool) *PrivateKey {
-+ pk := new(PrivateKey)
-+ pk.PublicKey = *NewDSAPublicKey(currentTime, &priv.PublicKey, isSubkey)
-+ pk.PrivateKey = priv
-+ return pk
-+}
-+
- func (pk *PrivateKey) parse(r io.Reader) (err error) {
- err = (&pk.PublicKey).parse(r)
- if err != nil {
-@@ -121,6 +128,8 @@
- switch priv := pk.PrivateKey.(type) {
- case *rsa.PrivateKey:
- err = serializeRSAPrivateKey(privateKeyBuf, priv)
-+ case *dsa.PrivateKey:
-+ err = serializeDSAPrivateKey(privateKeyBuf, priv)
- default:
- err = error_.InvalidArgumentError("non-RSA private key")
- }
-@@ -172,6 +181,10 @@
- return writeBig(w, priv.Precomputed.Qinv)
- }
-
-+func serializeDSAPrivateKey(w io.Writer, priv *dsa.PrivateKey) error {
-+ return writeBig(w, priv.X)
-+}
-+
- // Decrypt decrypts an encrypted private key using a passphrase.
- func (pk *PrivateKey) Decrypt(passphrase []byte) error {
- if !pk.Encrypted {
-diff -r 7ec969250bfc src/pkg/crypto/openpgp/packet/public_key.go
---- a/src/pkg/crypto/openpgp/packet/public_key.go Tue Dec 27 09:49:19 2011 -0500
-+++ b/src/pkg/crypto/openpgp/packet/public_key.go Sat Dec 31 02:32:45 2011 +0100
-@@ -53,6 +53,23 @@
- return pk
- }
-
-+// NewDSAPublicKey returns a PublicKey that wraps the given rsa.PublicKey.
-+func NewDSAPublicKey(creationTime time.Time, pub *dsa.PublicKey, isSubkey bool) *PublicKey {
-+ pk := &PublicKey{
-+ CreationTime: creationTime,
-+ PubKeyAlgo: PubKeyAlgoDSA,
-+ PublicKey: pub,
-+ IsSubkey: isSubkey,
-+ p: fromBig(pub.P),
-+ q: fromBig(pub.Q),
-+ g: fromBig(pub.G),
-+ y: fromBig(pub.Y),
-+ }
-+
-+ pk.setFingerPrintAndKeyId()
-+ return pk
-+}
-+
- func (pk *PublicKey) parse(r io.Reader) (err error) {
- // RFC 4880, section 5.5.2
- var buf [6]byte
-@@ -291,7 +308,14 @@
- return nil
- case PubKeyAlgoDSA:
- dsaPublicKey, _ := pk.PublicKey.(*dsa.PublicKey)
-- if !dsa.Verify(dsaPublicKey, hashBytes, new(big.Int).SetBytes(sig.DSASigR.bytes), new(big.Int).SetBytes(sig.DSASigS.bytes)) {
-+ // Hash truncation according to FIPS 186-3 section 4.6
-+ // Assuming Q.BitLen() is a multiple of 8
-+ n := len(hashBytes)
-+ k := dsaPublicKey.Q.BitLen() / 8
-+ if n > k {
-+ n = k
-+ }
-+ if !dsa.Verify(dsaPublicKey, hashBytes[:n], new(big.Int).SetBytes(sig.DSASigR.bytes), new(big.Int).SetBytes(sig.DSASigS.bytes)) {
- return error_.SignatureError("DSA verification failure")
- }
- return nil
+++ /dev/null
-diff -r 7ec969250bfc src/pkg/crypto/openpgp/packet/signature.go
---- a/src/pkg/crypto/openpgp/packet/signature.go Tue Dec 27 09:49:19 2011 -0500
-+++ b/src/pkg/crypto/openpgp/packet/signature.go Sat Dec 31 02:32:41 2011 +0100
-@@ -164,7 +164,7 @@
- const (
- creationTimeSubpacket signatureSubpacketType = 2
- signatureExpirationSubpacket signatureSubpacketType = 3
-- keyExpirySubpacket signatureSubpacketType = 9
-+ keyExpirationSubpacket signatureSubpacketType = 9
- prefSymmetricAlgosSubpacket signatureSubpacketType = 11
- issuerSubpacket signatureSubpacketType = 16
- prefHashAlgosSubpacket signatureSubpacketType = 21
-@@ -225,11 +225,7 @@
- return
- }
- t := binary.BigEndian.Uint32(subpacket)
-- if t == 0 {
-- sig.CreationTime = time.Time{}
-- } else {
-- sig.CreationTime = time.Unix(int64(t), 0)
-- }
-+ sig.CreationTime = time.Unix(int64(t), 0)
- case signatureExpirationSubpacket:
- // Signature expiration time, section 5.2.3.10
- if !isHashed {
-@@ -241,7 +237,7 @@
- }
- sig.SigLifetimeSecs = new(uint32)
- *sig.SigLifetimeSecs = binary.BigEndian.Uint32(subpacket)
-- case keyExpirySubpacket:
-+ case keyExpirationSubpacket:
- // Key expiration time, section 5.2.3.6
- if !isHashed {
- return
-@@ -443,7 +439,15 @@
- sig.RSASignature.bytes, err = rsa.SignPKCS1v15(rand.Reader, priv.PrivateKey.(*rsa.PrivateKey), sig.Hash, digest)
- sig.RSASignature.bitLength = uint16(8 * len(sig.RSASignature.bytes))
- case PubKeyAlgoDSA:
-- r, s, err := dsa.Sign(rand.Reader, priv.PrivateKey.(*dsa.PrivateKey), digest)
-+ dsaPrivateKey := priv.PrivateKey.(*dsa.PrivateKey)
-+ // Hash truncation according to FIPS 186-3 section 4.6
-+ // Assuming Q.BitLen() is a multiple of 8
-+ n := len(digest)
-+ k := dsaPrivateKey.Q.BitLen() / 8
-+ if n > k {
-+ n = k
-+ }
-+ r, s, err := dsa.Sign(rand.Reader, dsaPrivateKey, digest[:n])
- if err == nil {
- sig.DSASigR.bytes = r.Bytes()
- sig.DSASigR.bitLength = uint16(8 * len(sig.DSASigR.bytes))
-@@ -556,5 +560,59 @@
- subpackets = append(subpackets, outputSubpacket{true, issuerSubpacket, false, keyId})
- }
-
-+ if sig.SigLifetimeSecs != nil && *sig.SigLifetimeSecs != 0 {
-+ sigLifetime := make([]byte, 4)
-+ binary.BigEndian.PutUint32(sigLifetime, *sig.SigLifetimeSecs)
-+ // signature expiration is marked as critical
-+ subpackets = append(subpackets, outputSubpacket{true, signatureExpirationSubpacket, true, sigLifetime})
-+ }
-+
-+ // The following subpackets may only appear in self-signatures
-+
-+ if sig.KeyLifetimeSecs != nil && *sig.KeyLifetimeSecs != 0 {
-+ keyLifetime := make([]byte, 4)
-+ binary.BigEndian.PutUint32(keyLifetime, *sig.KeyLifetimeSecs)
-+ // TODO:
-+ // key expiration is marked as critical
-+ subpackets = append(subpackets, outputSubpacket{true, keyExpirationSubpacket, true, keyLifetime})
-+ }
-+
-+ if sig.IsPrimaryId != nil && *sig.IsPrimaryId {
-+ subpackets = append(subpackets, outputSubpacket{true, primaryUserIdSubpacket, false, []byte{1}})
-+ }
-+
-+ // []byte slices of preferred algorithms are not copied
-+
-+ if len(sig.PreferredSymmetric) > 0 {
-+ subpackets = append(subpackets, outputSubpacket{true, prefSymmetricAlgosSubpacket, false, sig.PreferredSymmetric})
-+ }
-+
-+ if len(sig.PreferredHash) > 0 {
-+ subpackets = append(subpackets, outputSubpacket{true, prefHashAlgosSubpacket, false, sig.PreferredHash})
-+ }
-+
-+ if len(sig.PreferredCompression) > 0 {
-+ subpackets = append(subpackets, outputSubpacket{true, prefCompressionSubpacket, false, sig.PreferredCompression})
-+ }
-+
-+ // The Key Flags subpacket may only appear in self-signatures or certification signatures
-+
-+ if sig.FlagsValid {
-+ flags := byte(0)
-+ if sig.FlagCertify {
-+ flags |= 1
-+ }
-+ if sig.FlagSign {
-+ flags |= 2
-+ }
-+ if sig.FlagEncryptCommunications {
-+ flags |= 4
-+ }
-+ if sig.FlagEncryptStorage {
-+ flags |= 8
-+ }
-+ subpackets = append(subpackets, outputSubpacket{true, keyFlagsSubpacket, false, []byte{flags}})
-+ }
-+
- return
- }