diff options
author | Ian Lance Taylor <ian@gcc.gnu.org> | 2011-03-30 15:33:16 +0000 |
---|---|---|
committer | Ian Lance Taylor <ian@gcc.gnu.org> | 2011-03-30 15:33:16 +0000 |
commit | f72f4169133572cf62f1e872c5657cdbc4d5de2c (patch) | |
tree | 9382d76e5dc68294cdf3c4f2c03a9f61b44fb014 /libgo/go/crypto | |
parent | f2034d064c29d9620c5562b2b5b517bdc6c7a672 (diff) | |
download | gcc-f72f4169133572cf62f1e872c5657cdbc4d5de2c.zip gcc-f72f4169133572cf62f1e872c5657cdbc4d5de2c.tar.gz gcc-f72f4169133572cf62f1e872c5657cdbc4d5de2c.tar.bz2 |
Update to current Go library.
From-SVN: r171732
Diffstat (limited to 'libgo/go/crypto')
-rw-r--r-- | libgo/go/crypto/cipher/ctr.go | 4 | ||||
-rw-r--r-- | libgo/go/crypto/ecdsa/ecdsa_test.go | 11 | ||||
-rw-r--r-- | libgo/go/crypto/elliptic/elliptic_test.go | 3 | ||||
-rw-r--r-- | libgo/go/crypto/openpgp/s2k/s2k_test.go | 3 | ||||
-rw-r--r-- | libgo/go/crypto/rand/rand_test.go | 6 | ||||
-rw-r--r-- | libgo/go/crypto/rsa/pkcs1v15_test.go | 6 | ||||
-rw-r--r-- | libgo/go/crypto/rsa/rsa_test.go | 9 | ||||
-rw-r--r-- | libgo/go/crypto/tls/common.go | 8 | ||||
-rw-r--r-- | libgo/go/crypto/tls/conn.go | 4 | ||||
-rw-r--r-- | libgo/go/crypto/tls/handshake_client.go | 33 | ||||
-rw-r--r-- | libgo/go/crypto/tls/handshake_client_test.go | 2 | ||||
-rw-r--r-- | libgo/go/crypto/tls/handshake_messages_test.go | 6 | ||||
-rw-r--r-- | libgo/go/crypto/tls/tls.go | 5 | ||||
-rw-r--r-- | libgo/go/crypto/x509/x509.go | 77 |
14 files changed, 164 insertions, 13 deletions
diff --git a/libgo/go/crypto/cipher/ctr.go b/libgo/go/crypto/cipher/ctr.go index 04436ec..147b74f 100644 --- a/libgo/go/crypto/cipher/ctr.go +++ b/libgo/go/crypto/cipher/ctr.go @@ -22,6 +22,10 @@ type ctr struct { // NewCTR returns a Stream which encrypts/decrypts using the given Block in // counter mode. The length of iv must be the same as the Block's block size. func NewCTR(block Block, iv []byte) Stream { + if len(iv) != block.BlockSize() { + panic("cipher.NewCTR: iv length must equal block size") + } + return &ctr{ b: block, ctr: dup(iv), diff --git a/libgo/go/crypto/ecdsa/ecdsa_test.go b/libgo/go/crypto/ecdsa/ecdsa_test.go index cc22b7a..d6b4039 100644 --- a/libgo/go/crypto/ecdsa/ecdsa_test.go +++ b/libgo/go/crypto/ecdsa/ecdsa_test.go @@ -20,12 +20,15 @@ func testKeyGeneration(t *testing.T, c *elliptic.Curve, tag string) { return } if !c.IsOnCurve(priv.PublicKey.X, priv.PublicKey.Y) { - t.Errorf("%s: public key invalid", tag, err) + t.Errorf("%s: public key invalid: %s", tag, err) } } func TestKeyGeneration(t *testing.T) { testKeyGeneration(t, elliptic.P224(), "p224") + if testing.Short() { + return + } testKeyGeneration(t, elliptic.P256(), "p256") testKeyGeneration(t, elliptic.P384(), "p384") testKeyGeneration(t, elliptic.P521(), "p521") @@ -53,6 +56,9 @@ func testSignAndVerify(t *testing.T, c *elliptic.Curve, tag string) { func TestSignAndVerify(t *testing.T) { testSignAndVerify(t, elliptic.P224(), "p224") + if testing.Short() { + return + } testSignAndVerify(t, elliptic.P256(), "p256") testSignAndVerify(t, elliptic.P384(), "p384") testSignAndVerify(t, elliptic.P521(), "p521") @@ -214,5 +220,8 @@ func TestVectors(t *testing.T) { if Verify(&pub, hashed, r, s) != test.ok { t.Errorf("%d: bad result", i) } + if testing.Short() { + break + } } } diff --git a/libgo/go/crypto/elliptic/elliptic_test.go b/libgo/go/crypto/elliptic/elliptic_test.go index 6ae6fb9..02083a9 100644 --- a/libgo/go/crypto/elliptic/elliptic_test.go +++ b/libgo/go/crypto/elliptic/elliptic_test.go @@ -297,6 +297,9 @@ func TestBaseMult(t *testing.T) { if fmt.Sprintf("%x", x) != e.x || fmt.Sprintf("%x", y) != e.y { t.Errorf("%d: bad output for k=%s: got (%x, %s), want (%s, %s)", i, e.k, x, y, e.x, e.y) } + if testing.Short() && i > 5 { + break + } } } diff --git a/libgo/go/crypto/openpgp/s2k/s2k_test.go b/libgo/go/crypto/openpgp/s2k/s2k_test.go index 814b786..75bc47e 100644 --- a/libgo/go/crypto/openpgp/s2k/s2k_test.go +++ b/libgo/go/crypto/openpgp/s2k/s2k_test.go @@ -90,5 +90,8 @@ func TestParse(t *testing.T) { if !bytes.Equal(out, expected) { t.Errorf("%d: output got: %x want: %x", i, out, expected) } + if testing.Short() { + break + } } } diff --git a/libgo/go/crypto/rand/rand_test.go b/libgo/go/crypto/rand/rand_test.go index f64ead4..bfae7ce 100644 --- a/libgo/go/crypto/rand/rand_test.go +++ b/libgo/go/crypto/rand/rand_test.go @@ -11,7 +11,11 @@ import ( ) func TestRead(t *testing.T) { - b := make([]byte, 4e6) + var n int = 4e6 + if testing.Short() { + n = 1e5 + } + b := make([]byte, n) n, err := Read(b) if n != len(b) || err != nil { t.Fatalf("Read(buf) = %d, %s", n, err) diff --git a/libgo/go/crypto/rsa/pkcs1v15_test.go b/libgo/go/crypto/rsa/pkcs1v15_test.go index 7b2ce08..30a4824 100644 --- a/libgo/go/crypto/rsa/pkcs1v15_test.go +++ b/libgo/go/crypto/rsa/pkcs1v15_test.go @@ -97,7 +97,11 @@ func TestEncryptPKCS1v15(t *testing.T) { return true } - quick.Check(tryEncryptDecrypt, nil) + config := new(quick.Config) + if testing.Short() { + config.MaxCount = 10 + } + quick.Check(tryEncryptDecrypt, config) } // These test vectors were generated with `openssl rsautl -pkcs -encrypt` diff --git a/libgo/go/crypto/rsa/rsa_test.go b/libgo/go/crypto/rsa/rsa_test.go index 22d4576..bf7c051 100644 --- a/libgo/go/crypto/rsa/rsa_test.go +++ b/libgo/go/crypto/rsa/rsa_test.go @@ -15,7 +15,11 @@ import ( func TestKeyGeneration(t *testing.T) { random := rand.Reader - priv, err := GenerateKey(random, 1024) + size := 1024 + if testing.Short() { + size = 128 + } + priv, err := GenerateKey(random, size) if err != nil { t.Errorf("failed to generate key") } @@ -99,6 +103,9 @@ func TestDecryptOAEP(t *testing.T) { t.Errorf("#%d,%d (blind) bad result: %#v (want %#v)", i, j, out, message.in) } } + if testing.Short() { + break + } } } diff --git a/libgo/go/crypto/tls/common.go b/libgo/go/crypto/tls/common.go index 81b5a07..c779234 100644 --- a/libgo/go/crypto/tls/common.go +++ b/libgo/go/crypto/tls/common.go @@ -93,9 +93,10 @@ const ( // ConnectionState records basic TLS details about the connection. type ConnectionState struct { - HandshakeComplete bool - CipherSuite uint16 - NegotiatedProtocol string + HandshakeComplete bool + CipherSuite uint16 + NegotiatedProtocol string + NegotiatedProtocolIsMutual bool // the certificate chain that was presented by the other side PeerCertificates []*x509.Certificate @@ -124,7 +125,6 @@ type Config struct { RootCAs *CASet // NextProtos is a list of supported, application level protocols. - // Currently only server-side handling is supported. NextProtos []string // ServerName is included in the client's handshake to support virtual diff --git a/libgo/go/crypto/tls/conn.go b/libgo/go/crypto/tls/conn.go index 1e6fe60..b94e235 100644 --- a/libgo/go/crypto/tls/conn.go +++ b/libgo/go/crypto/tls/conn.go @@ -35,7 +35,8 @@ type Conn struct { ocspResponse []byte // stapled OCSP response peerCertificates []*x509.Certificate - clientProtocol string + clientProtocol string + clientProtocolFallback bool // first permanent error errMutex sync.Mutex @@ -761,6 +762,7 @@ func (c *Conn) ConnectionState() ConnectionState { state.HandshakeComplete = c.handshakeComplete if c.handshakeComplete { state.NegotiatedProtocol = c.clientProtocol + state.NegotiatedProtocolIsMutual = !c.clientProtocolFallback state.CipherSuite = c.cipherSuite state.PeerCertificates = c.peerCertificates } diff --git a/libgo/go/crypto/tls/handshake_client.go b/libgo/go/crypto/tls/handshake_client.go index a325a9b..540b25c 100644 --- a/libgo/go/crypto/tls/handshake_client.go +++ b/libgo/go/crypto/tls/handshake_client.go @@ -29,6 +29,7 @@ func (c *Conn) clientHandshake() os.Error { serverName: c.config.ServerName, supportedCurves: []uint16{curveP256, curveP384, curveP521}, supportedPoints: []uint8{pointFormatUncompressed}, + nextProtoNeg: len(c.config.NextProtos) > 0, } t := uint32(c.config.time()) @@ -66,6 +67,11 @@ func (c *Conn) clientHandshake() os.Error { return c.sendAlert(alertUnexpectedMessage) } + if !hello.nextProtoNeg && serverHello.nextProtoNeg { + c.sendAlert(alertHandshakeFailure) + return os.ErrorString("server advertised unrequested NPN") + } + suite, suiteId := mutualCipherSuite(c.config.cipherSuites(), serverHello.cipherSuite) if suite == nil { return c.sendAlert(alertHandshakeFailure) @@ -267,6 +273,17 @@ func (c *Conn) clientHandshake() os.Error { c.out.prepareCipherSpec(clientCipher, clientHash) c.writeRecord(recordTypeChangeCipherSpec, []byte{1}) + if serverHello.nextProtoNeg { + nextProto := new(nextProtoMsg) + proto, fallback := mutualProtocol(c.config.NextProtos, serverHello.nextProtos) + nextProto.proto = proto + c.clientProtocol = proto + c.clientProtocolFallback = fallback + + finishedHash.Write(nextProto.marshal()) + c.writeRecord(recordTypeHandshake, nextProto.marshal()) + } + finished := new(finishedMsg) finished.verifyData = finishedHash.clientSum(masterSecret) finishedHash.Write(finished.marshal()) @@ -299,3 +316,19 @@ func (c *Conn) clientHandshake() os.Error { c.cipherSuite = suiteId return nil } + +// mutualProtocol finds the mutual Next Protocol Negotiation protocol given the +// set of client and server supported protocols. The set of client supported +// protocols must not be empty. It returns the resulting protocol and flag +// indicating if the fallback case was reached. +func mutualProtocol(clientProtos, serverProtos []string) (string, bool) { + for _, s := range serverProtos { + for _, c := range clientProtos { + if s == c { + return s, false + } + } + } + + return clientProtos[0], true +} diff --git a/libgo/go/crypto/tls/handshake_client_test.go b/libgo/go/crypto/tls/handshake_client_test.go index fd1f145..3f91c7a 100644 --- a/libgo/go/crypto/tls/handshake_client_test.go +++ b/libgo/go/crypto/tls/handshake_client_test.go @@ -50,7 +50,7 @@ func TestRunClient(t *testing.T) { testConfig.CipherSuites = []uint16{TLS_ECDHE_RSA_WITH_RC4_128_SHA} - conn, err := Dial("tcp", "", "127.0.0.1:10443", testConfig) + conn, err := Dial("tcp", "127.0.0.1:10443", testConfig) if err != nil { t.Fatal(err) } diff --git a/libgo/go/crypto/tls/handshake_messages_test.go b/libgo/go/crypto/tls/handshake_messages_test.go index 21577dd..0b93b89 100644 --- a/libgo/go/crypto/tls/handshake_messages_test.go +++ b/libgo/go/crypto/tls/handshake_messages_test.go @@ -34,7 +34,11 @@ func TestMarshalUnmarshal(t *testing.T) { for i, iface := range tests { ty := reflect.NewValue(iface).Type() - for j := 0; j < 100; j++ { + n := 100 + if testing.Short() { + n = 5 + } + for j := 0; j < n; j++ { v, ok := quick.Value(ty, rand) if !ok { t.Errorf("#%d: failed to create value", i) diff --git a/libgo/go/crypto/tls/tls.go b/libgo/go/crypto/tls/tls.go index e8290d7..f66449c 100644 --- a/libgo/go/crypto/tls/tls.go +++ b/libgo/go/crypto/tls/tls.go @@ -87,8 +87,9 @@ func Listen(network, laddr string, config *Config) (*Listener, os.Error) { // Dial interprets a nil configuration as equivalent to // the zero configuration; see the documentation of Config // for the defaults. -func Dial(network, laddr, raddr string, config *Config) (*Conn, os.Error) { - c, err := net.Dial(network, laddr, raddr) +func Dial(network, addr string, config *Config) (*Conn, os.Error) { + raddr := addr + c, err := net.Dial(network, raddr) if err != nil { return nil, err } diff --git a/libgo/go/crypto/x509/x509.go b/libgo/go/crypto/x509/x509.go index 3af8ba8..853bcde 100644 --- a/libgo/go/crypto/x509/x509.go +++ b/libgo/go/crypto/x509/x509.go @@ -304,6 +304,42 @@ const ( KeyUsageDecipherOnly ) +// RFC 5280, 4.2.1.12 Extended Key Usage +// +// anyExtendedKeyUsage OBJECT IDENTIFIER ::= { id-ce-extKeyUsage 0 } +// +// id-kp OBJECT IDENTIFIER ::= { id-pkix 3 } +// +// id-kp-serverAuth OBJECT IDENTIFIER ::= { id-kp 1 } +// id-kp-clientAuth OBJECT IDENTIFIER ::= { id-kp 2 } +// id-kp-codeSigning OBJECT IDENTIFIER ::= { id-kp 3 } +// id-kp-emailProtection OBJECT IDENTIFIER ::= { id-kp 4 } +// id-kp-timeStamping OBJECT IDENTIFIER ::= { id-kp 8 } +// id-kp-OCSPSigning OBJECT IDENTIFIER ::= { id-kp 9 } +var ( + oidExtKeyUsageAny = asn1.ObjectIdentifier{2, 5, 29, 37, 0} + oidExtKeyUsageServerAuth = asn1.ObjectIdentifier{1, 3, 6, 1, 5, 5, 7, 3, 1} + oidExtKeyUsageClientAuth = asn1.ObjectIdentifier{1, 3, 6, 1, 5, 5, 7, 3, 2} + oidExtKeyUsageCodeSigning = asn1.ObjectIdentifier{1, 3, 6, 1, 5, 5, 7, 3, 3} + oidExtKeyUsageEmailProtection = asn1.ObjectIdentifier{1, 3, 6, 1, 5, 5, 7, 3, 4} + oidExtKeyUsageTimeStamping = asn1.ObjectIdentifier{1, 3, 6, 1, 5, 5, 7, 3, 8} + oidExtKeyUsageOCSPSigning = asn1.ObjectIdentifier{1, 3, 6, 1, 5, 5, 7, 3, 9} +) + +// ExtKeyUsage represents an extended set of actions that are valid for a given key. +// Each of the ExtKeyUsage* constants define a unique action. +type ExtKeyUsage int + +const ( + ExtKeyUsageAny ExtKeyUsage = iota + ExtKeyUsageServerAuth + ExtKeyUsageClientAuth + ExtKeyUsageCodeSigning + ExtKeyUsageEmailProtection + ExtKeyUsageTimeStamping + ExtKeyUsageOCSPSigning +) + // A Certificate represents an X.509 certificate. type Certificate struct { Raw []byte // Raw ASN.1 DER contents. @@ -320,6 +356,9 @@ type Certificate struct { NotBefore, NotAfter *time.Time // Validity bounds. KeyUsage KeyUsage + ExtKeyUsage []ExtKeyUsage // Sequence of extended key usages. + UnknownExtKeyUsage []asn1.ObjectIdentifier // Encountered extended key usages unknown to this package. + BasicConstraintsValid bool // if true then the next two fields are valid. IsCA bool MaxPathLen int @@ -666,6 +705,44 @@ func parseCertificate(in *certificate) (*Certificate, os.Error) { out.AuthorityKeyId = a.Id continue + case 37: + // RFC 5280, 4.2.1.12. Extended Key Usage + + // id-ce-extKeyUsage OBJECT IDENTIFIER ::= { id-ce 37 } + // + // ExtKeyUsageSyntax ::= SEQUENCE SIZE (1..MAX) OF KeyPurposeId + // + // KeyPurposeId ::= OBJECT IDENTIFIER + + var keyUsage []asn1.ObjectIdentifier + _, err = asn1.Unmarshal(e.Value, &keyUsage) + if err != nil { + return nil, err + } + + for _, u := range keyUsage { + switch { + case u.Equal(oidExtKeyUsageAny): + out.ExtKeyUsage = append(out.ExtKeyUsage, ExtKeyUsageAny) + case u.Equal(oidExtKeyUsageServerAuth): + out.ExtKeyUsage = append(out.ExtKeyUsage, ExtKeyUsageServerAuth) + case u.Equal(oidExtKeyUsageClientAuth): + out.ExtKeyUsage = append(out.ExtKeyUsage, ExtKeyUsageClientAuth) + case u.Equal(oidExtKeyUsageCodeSigning): + out.ExtKeyUsage = append(out.ExtKeyUsage, ExtKeyUsageCodeSigning) + case u.Equal(oidExtKeyUsageEmailProtection): + out.ExtKeyUsage = append(out.ExtKeyUsage, ExtKeyUsageEmailProtection) + case u.Equal(oidExtKeyUsageTimeStamping): + out.ExtKeyUsage = append(out.ExtKeyUsage, ExtKeyUsageTimeStamping) + case u.Equal(oidExtKeyUsageOCSPSigning): + out.ExtKeyUsage = append(out.ExtKeyUsage, ExtKeyUsageOCSPSigning) + default: + out.UnknownExtKeyUsage = append(out.UnknownExtKeyUsage, u) + } + } + + continue + case 14: // RFC 5280, 4.2.1.2 var keyid []byte |