summaryrefslogtreecommitdiffhomepage
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/receive.go21
-rw-r--r--src/send.go7
-rw-r--r--src/tun.go14
-rw-r--r--src/tun_linux.go36
4 files changed, 60 insertions, 18 deletions
diff --git a/src/receive.go b/src/receive.go
index f650cc9..dbd2813 100644
--- a/src/receive.go
+++ b/src/receive.go
@@ -243,13 +243,24 @@ func (device *Device) RoutineDecryption() {
counter := elem.packet[MessageTransportOffsetCounter:MessageTransportOffsetContent]
content := elem.packet[MessageTransportOffsetContent:]
+ // expand nonce
+
+ nonce[0x4] = counter[0x0]
+ nonce[0x5] = counter[0x1]
+ nonce[0x6] = counter[0x2]
+ nonce[0x7] = counter[0x3]
+
+ nonce[0x8] = counter[0x4]
+ nonce[0x9] = counter[0x5]
+ nonce[0xa] = counter[0x6]
+ nonce[0xb] = counter[0x7]
+
// decrypt and release to consumer
var err error
- copy(nonce[4:], counter)
elem.counter = binary.LittleEndian.Uint64(counter)
elem.packet, err = elem.keyPair.receive.Open(
- elem.buffer[:0],
+ content[:0],
nonce[:],
content,
nil,
@@ -495,6 +506,7 @@ func (peer *Peer) RoutineSequentialReceiver() {
// wait for decryption
elem.mutex.Lock()
+
if elem.IsDropped() {
continue
}
@@ -603,8 +615,11 @@ func (peer *Peer) RoutineSequentialReceiver() {
// write to tun device
+ offset := MessageTransportOffsetContent
atomic.AddUint64(&peer.stats.rxBytes, uint64(len(elem.packet)))
- _, err := device.tun.device.Write(elem.packet)
+ _, err := device.tun.device.Write(
+ elem.buffer[:offset+len(elem.packet)],
+ offset)
device.PutMessageBuffer(elem.buffer)
if err != nil {
logError.Println("Failed to write packet to TUN device:", err)
diff --git a/src/send.go b/src/send.go
index 2919f2e..9537f5e 100644
--- a/src/send.go
+++ b/src/send.go
@@ -127,8 +127,9 @@ func (device *Device) RoutineReadFromTUN() {
// read packet
- elem.packet = elem.buffer[MessageTransportHeaderSize:]
- size, err := device.tun.device.Read(elem.packet)
+ offset := MessageTransportHeaderSize
+ size, err := device.tun.device.Read(elem.buffer[:], offset)
+
if err != nil {
logError.Println("Failed to read packet from TUN device:", err)
device.Close()
@@ -139,7 +140,7 @@ func (device *Device) RoutineReadFromTUN() {
continue
}
- elem.packet = elem.packet[:size]
+ elem.packet = elem.buffer[offset : offset+size]
// lookup peer
diff --git a/src/tun.go b/src/tun.go
index 215022c..54253b4 100644
--- a/src/tun.go
+++ b/src/tun.go
@@ -16,13 +16,13 @@ const (
)
type TUNDevice interface {
- File() *os.File // returns the file descriptor of the device
- Read([]byte) (int, error) // read a packet from the device (without any additional headers)
- Write([]byte) (int, error) // writes a packet to the device (without any additional headers)
- MTU() (int, error) // returns the MTU of the device
- Name() string // returns the current name
- Events() chan TUNEvent // returns a constant channel of events related to the device
- Close() error // stops the device and closes the event channel
+ File() *os.File // returns the file descriptor of the device
+ Read([]byte, int) (int, error) // read a packet from the device (without any additional headers)
+ Write([]byte, int) (int, error) // writes a packet to the device (without any additional headers)
+ MTU() (int, error) // returns the MTU of the device
+ Name() string // returns the current name
+ Events() chan TUNEvent // returns a constant channel of events related to the device
+ Close() error // stops the device and closes the event channel
}
func (device *Device) RoutineTUNEventReader() {
diff --git a/src/tun_linux.go b/src/tun_linux.go
index 8a5d53b..daa2462 100644
--- a/src/tun_linux.go
+++ b/src/tun_linux.go
@@ -7,6 +7,7 @@ import (
"encoding/binary"
"errors"
"fmt"
+ "golang.org/x/net/ipv6"
"golang.org/x/sys/unix"
"net"
"os"
@@ -249,16 +250,41 @@ func (tun *NativeTun) MTU() (int, error) {
return int(val), nil
}
-func (tun *NativeTun) Write(d []byte) (int, error) {
- return tun.fd.Write(d)
+func (tun *NativeTun) Write(buff []byte, offset int) (int, error) {
+
+ // reserve space for header
+
+ buff = buff[offset-4:]
+
+ // add packet information header
+
+ buff[0] = 0x00
+ buff[1] = 0x00
+
+ if buff[4] == ipv6.Version<<4 {
+ buff[2] = 0x86
+ buff[3] = 0xdd
+ } else {
+ buff[2] = 0x08
+ buff[3] = 0x00
+ }
+
+ // write
+
+ return tun.fd.Write(buff)
}
-func (tun *NativeTun) Read(d []byte) (int, error) {
+func (tun *NativeTun) Read(buff []byte, offset int) (int, error) {
select {
case err := <-tun.errors:
return 0, err
default:
- return tun.fd.Read(d)
+ buff := buff[offset-4:]
+ n, err := tun.fd.Read(buff[:])
+ if n < 4 {
+ return 0, err
+ }
+ return n - 4, err
}
}
@@ -306,7 +332,7 @@ func CreateTUN(name string) (TUNDevice, error) {
// create new device
var ifr [IFReqSize]byte
- var flags uint16 = unix.IFF_TUN | unix.IFF_NO_PI
+ var flags uint16 = unix.IFF_TUN // | unix.IFF_NO_PI
nameBytes := []byte(name)
if len(nameBytes) >= unix.IFNAMSIZ {
return nil, errors.New("Interface name too long")