// will use the optimised implementation in this file when possible. Instances
// of this type only exist when hasGCMAsm returns true.
type aesCipherGCM struct {
- aesCipher
+ aesCipherAsm
}
// NewGCM returns the AES cipher wrapped in Galois Counter Mode. This is only
c := &aesCipher{make([]uint32, n), make([]uint32, n)}
b.ResetTimer()
for i := 0; i < b.N; i++ {
- expandKey(tt.key, c.enc, c.dec)
+ expandKeyGo(tt.key, c.enc, c.dec)
}
}
case 16, 24, 32:
break
}
+ return newCipher(key)
+}
- n := k + 28
+// newCipherGeneric creates and returns a new cipher.Block
+// implemented in pure Go.
+func newCipherGeneric(key []byte) (cipher.Block, error) {
+ n := len(key) + 28
c := aesCipher{make([]uint32, n), make([]uint32, n)}
- expandKey(key, c.enc, c.dec)
-
- if hasGCMAsm() {
- return &aesCipherGCM{c}, nil
- }
-
+ expandKeyGo(key, c.enc, c.dec)
return &c, nil
}
if len(dst) < BlockSize {
panic("crypto/aes: output not full block")
}
- encryptBlock(c.enc, dst, src)
+ encryptBlockGo(c.enc, dst, src)
}
func (c *aesCipher) Decrypt(dst, src []byte) {
if len(dst) < BlockSize {
panic("crypto/aes: output not full block")
}
- decryptBlock(c.dec, dst, src)
+ decryptBlockGo(c.dec, dst, src)
}
--- /dev/null
+// Copyright 2012 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package aes
+
+import (
+ "crypto/cipher"
+)
+
+// defined in asm_amd64.s
+func hasAsm() bool
+func encryptBlockAsm(nr int, xk *uint32, dst, src *byte)
+func decryptBlockAsm(nr int, xk *uint32, dst, src *byte)
+func expandKeyAsm(nr int, key *byte, enc *uint32, dec *uint32)
+
+type aesCipherAsm struct {
+ aesCipher
+}
+
+var useAsm = hasAsm()
+
+func newCipher(key []byte) (cipher.Block, error) {
+ if !useAsm {
+ return newCipherGeneric(key)
+ }
+ n := len(key) + 28
+ c := aesCipherAsm{aesCipher{make([]uint32, n), make([]uint32, n)}}
+ rounds := 10
+ switch len(key) {
+ case 128 / 8:
+ rounds = 10
+ case 192 / 8:
+ rounds = 12
+ case 256 / 8:
+ rounds = 14
+ }
+ expandKeyAsm(rounds, &key[0], &c.enc[0], &c.dec[0])
+ if hasGCMAsm() {
+ return &aesCipherGCM{c}, nil
+ }
+
+ return &c, nil
+}
+
+func (c *aesCipherAsm) BlockSize() int { return BlockSize }
+
+func (c *aesCipherAsm) Encrypt(dst, src []byte) {
+ if len(src) < BlockSize {
+ panic("crypto/aes: input not full block")
+ }
+ if len(dst) < BlockSize {
+ panic("crypto/aes: output not full block")
+ }
+ encryptBlockAsm(len(c.enc)/4-1, &c.enc[0], &dst[0], &src[0])
+}
+
+func (c *aesCipherAsm) Decrypt(dst, src []byte) {
+ if len(src) < BlockSize {
+ panic("crypto/aes: input not full block")
+ }
+ if len(dst) < BlockSize {
+ panic("crypto/aes: output not full block")
+ }
+ decryptBlockAsm(len(c.dec)/4-1, &c.dec[0], &dst[0], &src[0])
+}
+++ /dev/null
-// Copyright 2012 The Go Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style
-// license that can be found in the LICENSE file.
-
-// +build amd64
-
-package aes
-
-// defined in asm_$GOARCH.s
-func hasAsm() bool
-func encryptBlockAsm(nr int, xk *uint32, dst, src *byte)
-func decryptBlockAsm(nr int, xk *uint32, dst, src *byte)
-func expandKeyAsm(nr int, key *byte, enc *uint32, dec *uint32)
-
-var useAsm = hasAsm()
-
-func encryptBlock(xk []uint32, dst, src []byte) {
- if useAsm {
- encryptBlockAsm(len(xk)/4-1, &xk[0], &dst[0], &src[0])
- } else {
- encryptBlockGo(xk, dst, src)
- }
-}
-
-func decryptBlock(xk []uint32, dst, src []byte) {
- if useAsm {
- decryptBlockAsm(len(xk)/4-1, &xk[0], &dst[0], &src[0])
- } else {
- decryptBlockGo(xk, dst, src)
- }
-}
-
-func expandKey(key []byte, enc, dec []uint32) {
- if useAsm {
- rounds := 10
- switch len(key) {
- case 128 / 8:
- rounds = 10
- case 192 / 8:
- rounds = 12
- case 256 / 8:
- rounds = 14
- }
- expandKeyAsm(rounds, &key[0], &enc[0], &dec[0])
- } else {
- expandKeyGo(key, enc, dec)
- }
-}
package aes
-func encryptBlock(xk []uint32, dst, src []byte) {
- encryptBlockGo(xk, dst, src)
-}
-
-func decryptBlock(xk []uint32, dst, src []byte) {
- decryptBlockGo(xk, dst, src)
-}
-
-func expandKey(key []byte, enc, dec []uint32) {
- expandKeyGo(key, enc, dec)
-}
-
-func hasGCMAsm() bool {
- return false
-}
+import (
+ "crypto/cipher"
+)
-type aesCipherGCM struct {
- aesCipher
+// newCipher calls the newCipherGeneric function
+// directly. Platforms with hardware accelerated
+// implementations of AES should implement their
+// own version of newCipher (which may then call
+// newCipherGeneric if needed).
+func newCipher(key []byte) (cipher.Block, error) {
+ return newCipherGeneric(key)
}