more progress:

* add tunnel crypto

* add base boilter plate for tunnel message processing
This commit is contained in:
Jeff Becker
2016-01-28 18:19:23 -05:00
parent 45656d356f
commit 3c62d42c42
9 changed files with 153 additions and 27 deletions

View File

@ -1,28 +1 @@
package crypto
type AesCBC struct {
}
type AesECB struct {
}
type TunnelKey [32]byte
type TunnelIV [16]byte
//
// tunnel aes base
//
type TunnelAes struct {
layerKey TunnelKey
ivKey TunnelKey
iv TunnelIV
}
type TunnelEncryption struct {
TunnelAes
}
type TunnelDecryption struct {
TunnelAes
}

49
lib/crypto/tunnel.go Normal file
View File

@ -0,0 +1,49 @@
package crypto
import (
"crypto/aes"
"crypto/cipher"
)
type TunnelData [1024]byte
// A symetric key for encrypting tunnel messages
type TunnelKey [32]byte
// The initialization vector for a tunnel message
type TunnelIV []byte
type Tunnel struct {
layerKey cipher.Block
ivKey cipher.Block
}
func NewTunnelCrypto(layerKey, ivKey TunnelKey) (t *Tunnel, err error) {
t = new(Tunnel)
t.layerKey, err = aes.NewCipher(layerKey[:])
if err == nil {
t.ivKey, err = aes.NewCipher(ivKey[:])
}
if err != nil {
// error happened we don't need t
t = nil
}
return
}
// encrypt tunnel data in place
func (t *Tunnel) Encrypt(td *TunnelData) {
data := *td
t.ivKey.Encrypt(data[16:1024], data[16:1024])
layerBlock := cipher.NewCBCEncrypter(t.layerKey, data[:16])
layerBlock.CryptBlocks(data[16:1024], data[16:1024])
t.ivKey.Encrypt(data[16:1024], data[16:1024])
}
func (t *Tunnel) Decrypt(td *TunnelData) {
data := *td
t.ivKey.Decrypt(data[16:1024], data[16:1024])
layerBlock := cipher.NewCBCDecrypter(t.layerKey, data[:16])
layerBlock.CryptBlocks(data[16:1024], data[16:1024])
t.ivKey.Decrypt(data[16:1024], data[16:1024])
}

68
lib/tunnel/delivery.go Normal file
View File

@ -0,0 +1,68 @@
package tunnel
import(
"encoding/binary"
)
const (
DT_LOCAL = iota
DT_TUNNEL
DT_ROUTER
DT_UNUSED
)
type DelayFactor byte
type DeliveryInstructions []byte
func (di DeliveryInstructions) DeliveryType() byte {
return (di[0] & 0x30) >> 4
}
func (di DeliveryInstructions) IsFragmented() bool {
return (di[0] & 0x08) == 0x08
}
// get the tunnel id in this devilevery instrcutions or 0 if not applicable
func (di DeliveryInstructions) TunnelID() (tid uint32) {
if di.DeliveryType() == DT_TUNNEL {
// TODO(psi): what if this is 0?
tid = binary.BigEndian.Uint32(di[1:5])
}
return
}
// do we have a delay factor?
func (di DeliveryInstructions) HasDelay() bool {
return (di[0] & 0x10) == 0x10
}
// get the delay factor if it exists
func (di DeliveryInstructions) Delay() (d DelayFactor) {
if di.HasDelay() {
t := di.DeliveryType()
if t == DT_TUNNEL {
d = DelayFactor(di[37])
} else if t == DT_ROUTER {
d = DelayFactor(di[36])
}
}
return
}
func (di DeliveryInstructions) HasExtendedOptions() bool {
return (di[0] & 0x04) == 0x04
}
// get the to hash for these delivery instructions or nil if not applicable
func (di DeliveryInstructions) ToHash() (h []byte) {
t := di.DeliveryType()
if t == DT_TUNNEL {
h = di[5:37]
} else if t == DT_ROUTER || t == DT_LOCAL {
h = di[4:36]
}
return
}

4
lib/tunnel/doc.go Normal file
View File

@ -0,0 +1,4 @@
/*
i2p garlic tunnel implementation
*/
package tunnel

1
lib/tunnel/endpoint.go Normal file
View File

@ -0,0 +1 @@
package tunnel

1
lib/tunnel/gateway.go Normal file
View File

@ -0,0 +1 @@
package tunnel

20
lib/tunnel/message.go Normal file
View File

@ -0,0 +1,20 @@
package tunnel
import (
"github.com/bounce-chat/go-i2p/lib/crypto"
"encoding/binary"
)
type TunnelID uint32
// data sent down a tunnel
type TunnelMessage crypto.TunnelData
func (tm TunnelMessage) ID() (tid TunnelID) {
tid = TunnelID(binary.BigEndian.Uint32(tm[:4]))
return
}
func (tm TunnelMessage) IV() crypto.TunnelIV {
return tm[4:20]
}

10
lib/tunnel/participant.go Normal file
View File

@ -0,0 +1,10 @@
package tunnel
import (
"github.com/bounce-chat/go-i2p/lib/crypto"
)
type Participant struct {
decryption *crypto.Tunnel
}