diff --git a/_ref/KEY_GUIDE.html b/_ref/KEY_GUIDE.html
index 85ffcee..76c7a60 100644
--- a/_ref/KEY_GUIDE.html
+++ b/_ref/KEY_GUIDE.html
@@ -734,7 +734,7 @@ pre.rouge {
Table of Contents
diff --git a/cipher/aes/aes128/cbc/funcs.go b/cipher/aes/aes128/cbc/funcs.go
index ad84cf3..867e83a 100644
--- a/cipher/aes/aes128/cbc/funcs.go
+++ b/cipher/aes/aes128/cbc/funcs.go
@@ -2,16 +2,30 @@ package cbc
import (
`bytes`
+ gAes `crypto/aes`
+ gCipher `crypto/cipher`
`io`
+ `r00t2.io/sshkeys/cipher`
`r00t2.io/sshkeys/cipher/aes`
`r00t2.io/sshkeys/cipher/aes/aes128`
`r00t2.io/sshkeys/internal`
)
+// Setup populates a Cipher from a key. The key must include the IV suffixed to the actual key.
func (c *Cipher) Setup(key []byte) (err error) {
- // TODO
+ if key == nil || len(key) < aes128.KdfKeySize {
+ err = cipher.ErrBadKeyLen
+ return
+ }
+
+ if c == nil {
+ c = &Cipher{}
+ }
+
+ c.key = key[0:aes128.KeySize]
+ c.iv = key[aes128.KeySize:(aes128.KdfKeySize)]
return
}
@@ -67,6 +81,8 @@ func (c *Cipher) Encrypt(data interface{}) (encrypted *bytes.Reader, err error)
var b []byte
var cryptDst []byte
var padded *bytes.Reader
+ var cryptBlock gCipher.Block
+ var crypter gCipher.BlockMode
if b, err = internal.SerializeData(data); err != nil {
return
@@ -83,8 +99,14 @@ func (c *Cipher) Encrypt(data interface{}) (encrypted *bytes.Reader, err error)
cryptDst = make([]byte, len(b))
- // TODO
- _ = cryptDst
+ if cryptBlock, err = gAes.NewCipher(c.key); err != nil {
+ return
+ }
+ crypter = gCipher.NewCBCEncrypter(cryptBlock, c.iv)
+
+ crypter.CryptBlocks(cryptDst, b)
+
+ encrypted = bytes.NewReader(cryptDst)
return
}
@@ -135,7 +157,25 @@ func (c *Cipher) AllocateEncrypt(data interface{}) (encrypted *bytes.Reader, err
*/
func (c *Cipher) Pad(data interface{}) (paddedBuf *bytes.Reader, err error) {
- // TODO
+ var b []byte
+ var padNum int
+ var pad []byte
+ var buf *bytes.Buffer
+
+ if b, err = internal.UnpackBytes(data); err != nil {
+ return
+ }
+ buf = bytes.NewBuffer(b)
+
+ for padIdx := 1; (buf.Len() % aes.BlockSize) != 0; padIdx++ {
+
+ padNum = padIdx & cipher.PadMod
+ pad = []byte{byte(uint32(padNum))}
+
+ if _, err = buf.Write(pad); err != nil {
+ return
+ }
+ }
return
}
@@ -154,6 +194,8 @@ func (c *Cipher) Decrypt(data interface{}) (decrypted *bytes.Reader, err error)
var b []byte
var decryptDst []byte
+ var cryptBlock gCipher.Block
+ var decrypter gCipher.BlockMode
if b, err = internal.SerializeData(data); err != nil {
return
@@ -161,8 +203,14 @@ func (c *Cipher) Decrypt(data interface{}) (decrypted *bytes.Reader, err error)
decryptDst = make([]byte, len(b))
- // TODO
- _ = decryptDst
+ if cryptBlock, err = gAes.NewCipher(c.key); err != nil {
+ return
+ }
+ decrypter = gCipher.NewCBCDecrypter(cryptBlock, c.iv)
+
+ decrypter.CryptBlocks(decryptDst, b)
+
+ decrypted = bytes.NewReader(decryptDst)
return
}
diff --git a/cipher/aes/aes192/cbc/funcs.go b/cipher/aes/aes192/cbc/funcs.go
index ad84cf3..867e83a 100644
--- a/cipher/aes/aes192/cbc/funcs.go
+++ b/cipher/aes/aes192/cbc/funcs.go
@@ -2,16 +2,30 @@ package cbc
import (
`bytes`
+ gAes `crypto/aes`
+ gCipher `crypto/cipher`
`io`
+ `r00t2.io/sshkeys/cipher`
`r00t2.io/sshkeys/cipher/aes`
`r00t2.io/sshkeys/cipher/aes/aes128`
`r00t2.io/sshkeys/internal`
)
+// Setup populates a Cipher from a key. The key must include the IV suffixed to the actual key.
func (c *Cipher) Setup(key []byte) (err error) {
- // TODO
+ if key == nil || len(key) < aes128.KdfKeySize {
+ err = cipher.ErrBadKeyLen
+ return
+ }
+
+ if c == nil {
+ c = &Cipher{}
+ }
+
+ c.key = key[0:aes128.KeySize]
+ c.iv = key[aes128.KeySize:(aes128.KdfKeySize)]
return
}
@@ -67,6 +81,8 @@ func (c *Cipher) Encrypt(data interface{}) (encrypted *bytes.Reader, err error)
var b []byte
var cryptDst []byte
var padded *bytes.Reader
+ var cryptBlock gCipher.Block
+ var crypter gCipher.BlockMode
if b, err = internal.SerializeData(data); err != nil {
return
@@ -83,8 +99,14 @@ func (c *Cipher) Encrypt(data interface{}) (encrypted *bytes.Reader, err error)
cryptDst = make([]byte, len(b))
- // TODO
- _ = cryptDst
+ if cryptBlock, err = gAes.NewCipher(c.key); err != nil {
+ return
+ }
+ crypter = gCipher.NewCBCEncrypter(cryptBlock, c.iv)
+
+ crypter.CryptBlocks(cryptDst, b)
+
+ encrypted = bytes.NewReader(cryptDst)
return
}
@@ -135,7 +157,25 @@ func (c *Cipher) AllocateEncrypt(data interface{}) (encrypted *bytes.Reader, err
*/
func (c *Cipher) Pad(data interface{}) (paddedBuf *bytes.Reader, err error) {
- // TODO
+ var b []byte
+ var padNum int
+ var pad []byte
+ var buf *bytes.Buffer
+
+ if b, err = internal.UnpackBytes(data); err != nil {
+ return
+ }
+ buf = bytes.NewBuffer(b)
+
+ for padIdx := 1; (buf.Len() % aes.BlockSize) != 0; padIdx++ {
+
+ padNum = padIdx & cipher.PadMod
+ pad = []byte{byte(uint32(padNum))}
+
+ if _, err = buf.Write(pad); err != nil {
+ return
+ }
+ }
return
}
@@ -154,6 +194,8 @@ func (c *Cipher) Decrypt(data interface{}) (decrypted *bytes.Reader, err error)
var b []byte
var decryptDst []byte
+ var cryptBlock gCipher.Block
+ var decrypter gCipher.BlockMode
if b, err = internal.SerializeData(data); err != nil {
return
@@ -161,8 +203,14 @@ func (c *Cipher) Decrypt(data interface{}) (decrypted *bytes.Reader, err error)
decryptDst = make([]byte, len(b))
- // TODO
- _ = decryptDst
+ if cryptBlock, err = gAes.NewCipher(c.key); err != nil {
+ return
+ }
+ decrypter = gCipher.NewCBCDecrypter(cryptBlock, c.iv)
+
+ decrypter.CryptBlocks(decryptDst, b)
+
+ decrypted = bytes.NewReader(decryptDst)
return
}
diff --git a/cipher/aes/aes256/cbc/funcs.go b/cipher/aes/aes256/cbc/funcs.go
index ad84cf3..867e83a 100644
--- a/cipher/aes/aes256/cbc/funcs.go
+++ b/cipher/aes/aes256/cbc/funcs.go
@@ -2,16 +2,30 @@ package cbc
import (
`bytes`
+ gAes `crypto/aes`
+ gCipher `crypto/cipher`
`io`
+ `r00t2.io/sshkeys/cipher`
`r00t2.io/sshkeys/cipher/aes`
`r00t2.io/sshkeys/cipher/aes/aes128`
`r00t2.io/sshkeys/internal`
)
+// Setup populates a Cipher from a key. The key must include the IV suffixed to the actual key.
func (c *Cipher) Setup(key []byte) (err error) {
- // TODO
+ if key == nil || len(key) < aes128.KdfKeySize {
+ err = cipher.ErrBadKeyLen
+ return
+ }
+
+ if c == nil {
+ c = &Cipher{}
+ }
+
+ c.key = key[0:aes128.KeySize]
+ c.iv = key[aes128.KeySize:(aes128.KdfKeySize)]
return
}
@@ -67,6 +81,8 @@ func (c *Cipher) Encrypt(data interface{}) (encrypted *bytes.Reader, err error)
var b []byte
var cryptDst []byte
var padded *bytes.Reader
+ var cryptBlock gCipher.Block
+ var crypter gCipher.BlockMode
if b, err = internal.SerializeData(data); err != nil {
return
@@ -83,8 +99,14 @@ func (c *Cipher) Encrypt(data interface{}) (encrypted *bytes.Reader, err error)
cryptDst = make([]byte, len(b))
- // TODO
- _ = cryptDst
+ if cryptBlock, err = gAes.NewCipher(c.key); err != nil {
+ return
+ }
+ crypter = gCipher.NewCBCEncrypter(cryptBlock, c.iv)
+
+ crypter.CryptBlocks(cryptDst, b)
+
+ encrypted = bytes.NewReader(cryptDst)
return
}
@@ -135,7 +157,25 @@ func (c *Cipher) AllocateEncrypt(data interface{}) (encrypted *bytes.Reader, err
*/
func (c *Cipher) Pad(data interface{}) (paddedBuf *bytes.Reader, err error) {
- // TODO
+ var b []byte
+ var padNum int
+ var pad []byte
+ var buf *bytes.Buffer
+
+ if b, err = internal.UnpackBytes(data); err != nil {
+ return
+ }
+ buf = bytes.NewBuffer(b)
+
+ for padIdx := 1; (buf.Len() % aes.BlockSize) != 0; padIdx++ {
+
+ padNum = padIdx & cipher.PadMod
+ pad = []byte{byte(uint32(padNum))}
+
+ if _, err = buf.Write(pad); err != nil {
+ return
+ }
+ }
return
}
@@ -154,6 +194,8 @@ func (c *Cipher) Decrypt(data interface{}) (decrypted *bytes.Reader, err error)
var b []byte
var decryptDst []byte
+ var cryptBlock gCipher.Block
+ var decrypter gCipher.BlockMode
if b, err = internal.SerializeData(data); err != nil {
return
@@ -161,8 +203,14 @@ func (c *Cipher) Decrypt(data interface{}) (decrypted *bytes.Reader, err error)
decryptDst = make([]byte, len(b))
- // TODO
- _ = decryptDst
+ if cryptBlock, err = gAes.NewCipher(c.key); err != nil {
+ return
+ }
+ decrypter = gCipher.NewCBCDecrypter(cryptBlock, c.iv)
+
+ decrypter.CryptBlocks(decryptDst, b)
+
+ decrypted = bytes.NewReader(decryptDst)
return
}
diff --git a/cipher/consts.go b/cipher/consts.go
new file mode 100644
index 0000000..9833d30
--- /dev/null
+++ b/cipher/consts.go
@@ -0,0 +1,5 @@
+package cipher
+
+const (
+ PadMod int = 0xff
+)
diff --git a/cipher/errs.go b/cipher/errs.go
new file mode 100644
index 0000000..c1f8359
--- /dev/null
+++ b/cipher/errs.go
@@ -0,0 +1,9 @@
+package cipher
+
+import (
+ `errors`
+)
+
+var (
+ ErrBadKeyLen error = errors.New("the specified key does not match the Cipher.BlockSize size")
+)