summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--bind_test.go5
-rw-r--r--conn.go5
-rw-r--r--conn_default.go5
-rw-r--r--conn_linux.go4
-rw-r--r--constants.go5
-rw-r--r--cookie.go5
-rw-r--r--cookie_test.go5
-rw-r--r--daemon_darwin.go9
-rw-r--r--daemon_linux.go32
-rw-r--r--daemon_windows.go34
-rw-r--r--device.go5
-rw-r--r--device_test.go5
-rw-r--r--endpoint_test.go5
-rw-r--r--helper_test.go5
-rw-r--r--index.go5
-rw-r--r--ip.go5
-rw-r--r--kdf_test.go5
-rw-r--r--keypair.go5
-rw-r--r--logger.go5
-rw-r--r--main.go97
-rw-r--r--misc.go5
-rw-r--r--noise-helpers.go5
-rw-r--r--noise-protocol.go5
-rw-r--r--noise-types.go5
-rw-r--r--noise_test.go5
-rw-r--r--peer.go5
-rw-r--r--ratelimiter/ratelimiter.go9
-rw-r--r--ratelimiter/ratelimiter_test.go5
-rw-r--r--receive.go5
-rw-r--r--replay.go5
-rw-r--r--replay_test.go5
-rw-r--r--routing.go5
-rw-r--r--send.go5
-rw-r--r--signal.go5
-rw-r--r--tai64n/tai64n.go5
-rw-r--r--tai64n/tai64n_test.go5
-rw-r--r--timers.go5
-rw-r--r--trie.go5
-rw-r--r--trie_rand_test.go5
-rw-r--r--trie_test.go5
-rw-r--r--tun.go5
-rw-r--r--tun_darwin.go193
-rw-r--r--tun_linux.go5
-rw-r--r--tun_windows.go5
-rw-r--r--uapi.go5
-rw-r--r--uapi_darwin.go120
-rw-r--r--uapi_linux.go5
-rw-r--r--uapi_windows.go5
-rw-r--r--xchacha20poly1305/xchacha20.go8
-rw-r--r--xchacha20poly1305/xchacha20_test.go5
50 files changed, 491 insertions, 220 deletions
diff --git a/bind_test.go b/bind_test.go
index 41c4225..47f5492 100644
--- a/bind_test.go
+++ b/bind_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import "errors"
diff --git a/conn.go b/conn.go
index 6bb262c..082bbca 100644
--- a/conn.go
+++ b/conn.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/conn_default.go b/conn_default.go
index 5b73c90..047d5f6 100644
--- a/conn_default.go
+++ b/conn_default.go
@@ -1,5 +1,10 @@
// +build !linux
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/conn_linux.go b/conn_linux.go
index ff3c483..a428138 100644
--- a/conn_linux.go
+++ b/conn_linux.go
@@ -1,4 +1,6 @@
-/* Copyright 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
*
* This implements userspace semantics of "sticky sockets", modeled after
* WireGuard's kernelspace implementation. This is more or less a straight port
diff --git a/constants.go b/constants.go
index 8835f92..04b75d7 100644
--- a/constants.go
+++ b/constants.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/cookie.go b/cookie.go
index 813ddab..cfee367 100644
--- a/cookie.go
+++ b/cookie.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/cookie_test.go b/cookie_test.go
index d745fe7..34c8ad4 100644
--- a/cookie_test.go
+++ b/cookie_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/daemon_darwin.go b/daemon_darwin.go
deleted file mode 100644
index 913af0e..0000000
--- a/daemon_darwin.go
+++ /dev/null
@@ -1,9 +0,0 @@
-package main
-
-import (
- "errors"
-)
-
-func Daemonize() error {
- return errors.New("Not implemented on OSX")
-}
diff --git a/daemon_linux.go b/daemon_linux.go
deleted file mode 100644
index e1aaede..0000000
--- a/daemon_linux.go
+++ /dev/null
@@ -1,32 +0,0 @@
-package main
-
-import (
- "os"
- "os/exec"
-)
-
-/* Daemonizes the process on linux
- *
- * This is done by spawning and releasing a copy with the --foreground flag
- */
-func Daemonize(attr *os.ProcAttr) error {
- // I would like to use os.Executable,
- // however this means dropping support for Go <1.8
- path, err := exec.LookPath(os.Args[0])
- if err != nil {
- return err
- }
-
- argv := []string{os.Args[0], "--foreground"}
- argv = append(argv, os.Args[1:]...)
- process, err := os.StartProcess(
- path,
- argv,
- attr,
- )
- if err != nil {
- return err
- }
- process.Release()
- return nil
-}
diff --git a/daemon_windows.go b/daemon_windows.go
deleted file mode 100644
index 527718a..0000000
--- a/daemon_windows.go
+++ /dev/null
@@ -1,34 +0,0 @@
-package main
-
-import (
- "os"
-)
-
-/* Daemonizes the process on windows
- *
- * This is done by spawning and releasing a copy with the --foreground flag
- */
-
-func Daemonize() error {
- argv := []string{os.Args[0], "--foreground"}
- argv = append(argv, os.Args[1:]...)
- attr := &os.ProcAttr{
- Dir: ".",
- Env: os.Environ(),
- Files: []*os.File{
- os.Stdin,
- nil,
- nil,
- },
- }
- process, err := os.StartProcess(
- argv[0],
- argv,
- attr,
- )
- if err != nil {
- return err
- }
- process.Release()
- return nil
-}
diff --git a/device.go b/device.go
index dddb547..8b0d2a5 100644
--- a/device.go
+++ b/device.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/device_test.go b/device_test.go
index abd0208..7af52b2 100644
--- a/device_test.go
+++ b/device_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
/* Create two device instances and simulate full WireGuard interaction
diff --git a/endpoint_test.go b/endpoint_test.go
index 7021e48..5dd6cb4 100644
--- a/endpoint_test.go
+++ b/endpoint_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/helper_test.go b/helper_test.go
index 41e6b72..a8adcd7 100644
--- a/helper_test.go
+++ b/helper_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/index.go b/index.go
index 1ba040e..c309f23 100644
--- a/index.go
+++ b/index.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/ip.go b/ip.go
index 752a404..7be9337 100644
--- a/ip.go
+++ b/ip.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/kdf_test.go b/kdf_test.go
index a89dacc..fa4a2d2 100644
--- a/kdf_test.go
+++ b/kdf_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/keypair.go b/keypair.go
index 1ab0649..eaf30b2 100644
--- a/keypair.go
+++ b/keypair.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/logger.go b/logger.go
index 0872ef9..784235c 100644
--- a/logger.go
+++ b/logger.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/main.go b/main.go
index 7742eef..e7e0488 100644
--- a/main.go
+++ b/main.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
@@ -14,8 +19,9 @@ const (
)
const (
- ENV_WG_TUN_FD = "WG_TUN_FD"
- ENV_WG_UAPI_FD = "WG_UAPI_FD"
+ ENV_WG_TUN_FD = "WG_TUN_FD"
+ ENV_WG_UAPI_FD = "WG_UAPI_FD"
+ ENV_WG_PROCESS_FOREGROUND = "WG_PROCESS_FOREGROUND"
)
func printUsage() {
@@ -23,7 +29,45 @@ func printUsage() {
fmt.Printf("%s [-f/--foreground] INTERFACE-NAME\n", os.Args[0])
}
+func warning() {
+ shouldQuit := false
+
+ fmt.Fprintln(os.Stderr, "WARNING WARNING WARNING WARNING WARNING WARNING WARNING")
+ fmt.Fprintln(os.Stderr, "W G")
+ fmt.Fprintln(os.Stderr, "W This is alpha software. It will very likely not G")
+ fmt.Fprintln(os.Stderr, "W do what it is supposed to do, and things may go G")
+ fmt.Fprintln(os.Stderr, "W horribly wrong. You have been warned. Proceed G")
+ fmt.Fprintln(os.Stderr, "W at your own risk. G")
+ if runtime.GOOS == "linux" {
+ shouldQuit = os.Getenv("WG_I_PREFER_BUGGY_USERSPACE_TO_POLISHED_KMOD") != "1"
+
+ fmt.Fprintln(os.Stderr, "W G")
+ fmt.Fprintln(os.Stderr, "W Furthermore, you are running this software on a G")
+ fmt.Fprintln(os.Stderr, "W Linux kernel, which is probably unnecessary and G")
+ fmt.Fprintln(os.Stderr, "W foolish. This is because the Linux kernel has G")
+ fmt.Fprintln(os.Stderr, "W built-in first class support for WireGuard, and G")
+ fmt.Fprintln(os.Stderr, "W this support is much more refined than this G")
+ fmt.Fprintln(os.Stderr, "W program. For more information on installing the G")
+ fmt.Fprintln(os.Stderr, "W kernel module, please visit: G")
+ fmt.Fprintln(os.Stderr, "W https://www.wireguard.com/install G")
+ if shouldQuit {
+ fmt.Fprintln(os.Stderr, "W G")
+ fmt.Fprintln(os.Stderr, "W If you still want to use this program, against G")
+ fmt.Fprintln(os.Stderr, "W the sage advice here, please first export this G")
+ fmt.Fprintln(os.Stderr, "W environment variable: G")
+ fmt.Fprintln(os.Stderr, "W WG_I_PREFER_BUGGY_USERSPACE_TO_POLISHED_KMOD=1 G")
+ }
+ }
+ fmt.Fprintln(os.Stderr, "W G")
+ fmt.Fprintln(os.Stderr, "WARNING WARNING WARNING WARNING WARNING WARNING WARNING")
+
+ if shouldQuit {
+ os.Exit(1)
+ }
+}
+
func main() {
+ warning()
// parse arguments
@@ -53,6 +97,10 @@ func main() {
interfaceName = os.Args[1]
}
+ if !foreground {
+ foreground = os.Getenv(ENV_WG_PROCESS_FOREGROUND) == "1"
+ }
+
// get log level (default: info)
logLevel := func() int {
@@ -67,13 +115,6 @@ func main() {
return LogLevelInfo
}()
- logger := NewLogger(
- logLevel,
- fmt.Sprintf("(%s) ", interfaceName),
- )
-
- logger.Debug.Println("Debug log enabled")
-
// open TUN device (or use supplied fd)
tun, err := func() (TUNDevice, error) {
@@ -93,6 +134,21 @@ func main() {
return CreateTUNFromFile(file)
}()
+ if err == nil {
+ realInterfaceName, err2 := tun.Name()
+ if err2 == nil {
+ interfaceName = realInterfaceName
+ }
+ }
+
+ logger := NewLogger(
+ logLevel,
+ fmt.Sprintf("(%s) ", interfaceName),
+ )
+
+ logger.Debug.Println("Debug log enabled")
+
+
if err != nil {
logger.Error.Println("Failed to create TUN device:", err)
os.Exit(ExitSetupFailed)
@@ -127,6 +183,7 @@ func main() {
env := os.Environ()
env = append(env, fmt.Sprintf("%s=3", ENV_WG_TUN_FD))
env = append(env, fmt.Sprintf("%s=4", ENV_WG_UAPI_FD))
+ env = append(env, fmt.Sprintf("%s=1", ENV_WG_PROCESS_FOREGROUND))
attr := &os.ProcAttr{
Files: []*os.File{
nil, // stdin
@@ -138,18 +195,26 @@ func main() {
Dir: ".",
Env: env,
}
- err = Daemonize(attr)
+
+ path, err := os.Executable()
+ if err != nil {
+ logger.Error.Println("Failed to determine executable:", err)
+ os.Exit(ExitSetupFailed)
+ }
+
+ process, err := os.StartProcess(
+ path,
+ os.Args,
+ attr,
+ )
if err != nil {
logger.Error.Println("Failed to daemonize:", err)
os.Exit(ExitSetupFailed)
}
+ process.Release()
return
}
- // increase number of go workers (for Go <1.5)
-
- runtime.GOMAXPROCS(runtime.NumCPU())
-
// create wireguard device
device := NewDevice(tun, logger)
@@ -162,6 +227,10 @@ func main() {
term := make(chan os.Signal)
uapi, err := UAPIListen(interfaceName, fileUAPI)
+ if err != nil {
+ logger.Error.Println("Failed to listen on uapi socket:", err)
+ os.Exit(ExitSetupFailed)
+ }
go func() {
for {
diff --git a/misc.go b/misc.go
index 80e33f6..f94a617 100644
--- a/misc.go
+++ b/misc.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/noise-helpers.go b/noise-helpers.go
index 1e2de5f..6e23d83 100644
--- a/noise-helpers.go
+++ b/noise-helpers.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/noise-protocol.go b/noise-protocol.go
index 6440c97..b880ede 100644
--- a/noise-protocol.go
+++ b/noise-protocol.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/noise-types.go b/noise-types.go
index 1a944df..58aa0c2 100644
--- a/noise-types.go
+++ b/noise-types.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/noise_test.go b/noise_test.go
index 5e9d44b..958a4ef 100644
--- a/noise_test.go
+++ b/noise_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/peer.go b/peer.go
index 41d3ef1..d43f020 100644
--- a/peer.go
+++ b/peer.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/ratelimiter/ratelimiter.go b/ratelimiter/ratelimiter.go
index 006900a..1aa6813 100644
--- a/ratelimiter/ratelimiter.go
+++ b/ratelimiter/ratelimiter.go
@@ -1,8 +1,9 @@
-package ratelimiter
-
-/* Copyright (C) 2015-2017 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved. */
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
-/* This file contains a port of the rate-limiter from the linux kernel version */
+package ratelimiter
import (
"net"
diff --git a/ratelimiter/ratelimiter_test.go b/ratelimiter/ratelimiter_test.go
index 37339ee..9bdaa4d 100644
--- a/ratelimiter/ratelimiter_test.go
+++ b/ratelimiter/ratelimiter_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package ratelimiter
import (
diff --git a/receive.go b/receive.go
index e779012..3ce79b0 100644
--- a/receive.go
+++ b/receive.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/replay.go b/replay.go
index 5d42860..8fab1d2 100644
--- a/replay.go
+++ b/replay.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
/* Copyright (C) 2015-2017 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved. */
diff --git a/replay_test.go b/replay_test.go
index f697701..77180e5 100644
--- a/replay_test.go
+++ b/replay_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/routing.go b/routing.go
index 2a2e237..77c9b1e 100644
--- a/routing.go
+++ b/routing.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/send.go b/send.go
index 646550a..f99bdcd 100644
--- a/send.go
+++ b/send.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/signal.go b/signal.go
index d8d7153..606da52 100644
--- a/signal.go
+++ b/signal.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
func signalSend(s chan<- struct{}) {
diff --git a/tai64n/tai64n.go b/tai64n/tai64n.go
index da5257c..1c7f42b 100644
--- a/tai64n/tai64n.go
+++ b/tai64n/tai64n.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package tai64n
import (
diff --git a/tai64n/tai64n_test.go b/tai64n/tai64n_test.go
index 389b65c..62e7b1b 100644
--- a/tai64n/tai64n_test.go
+++ b/tai64n/tai64n_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package tai64n
import (
diff --git a/timers.go b/timers.go
index a336b2f..66827b6 100644
--- a/timers.go
+++ b/timers.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/trie.go b/trie.go
index 405ffc3..03f0722 100644
--- a/trie.go
+++ b/trie.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/trie_rand_test.go b/trie_rand_test.go
index 840d269..157c270 100644
--- a/trie_rand_test.go
+++ b/trie_rand_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/trie_test.go b/trie_test.go
index 9d53df3..3c3b5ba 100644
--- a/trie_test.go
+++ b/trie_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/tun.go b/tun.go
index 318772a..ec3ab47 100644
--- a/tun.go
+++ b/tun.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/tun_darwin.go b/tun_darwin.go
index 87f6af6..5514563 100644
--- a/tun_darwin.go
+++ b/tun_darwin.go
@@ -1,22 +1,17 @@
-/* Copyright (c) 2016, Song Gao <song@gao.io>
- * All rights reserved.
+/* SPDX-License-Identifier: GPL-2.0
*
- * Code from https://github.com/songgao/water
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
*/
package main
import (
"encoding/binary"
- "errors"
"fmt"
- "golang.org/x/net/ipv4"
"golang.org/x/net/ipv6"
"golang.org/x/sys/unix"
- "io"
"net"
"os"
- "sync"
"time"
"unsafe"
)
@@ -36,36 +31,32 @@ type sockaddrCtl struct {
scReserved [5]uint32
}
-// NativeTUN is a hack to work around the first 4 bytes "packet
+// NativeTun is a hack to work around the first 4 bytes "packet
// information" because there doesn't seem to be an IFF_NO_PI for darwin.
-type NativeTUN struct {
+type NativeTun struct {
name string
- f io.ReadWriteCloser
+ fd *os.File
mtu int
- rMu sync.Mutex
- rBuf []byte
-
- wMu sync.Mutex
- wBuf []byte
-
events chan TUNEvent
errors chan error
}
var sockaddrCtlSize uintptr = 32
-func CreateTUN(name string) (ifce TUNDevice, err error) {
+func CreateTUN(name string) (TUNDevice, error) {
ifIndex := -1
- fmt.Sscanf(name, "utun%d", &ifIndex)
- if ifIndex < 0 {
- return nil, fmt.Errorf("error parsing interface name %s, must be utun[0-9]+", name)
+ if (name != "utun") {
+ fmt.Sscanf(name, "utun%d", &ifIndex)
+ if ifIndex < 0 {
+ return nil, fmt.Errorf("Interface name must be utun[0-9]*")
+ }
}
fd, err := unix.Socket(unix.AF_SYSTEM, unix.SOCK_DGRAM, 2)
if err != nil {
- return nil, fmt.Errorf("error in unix.Socket: %v", err)
+ return nil, err
}
var ctlInfo = &struct {
@@ -83,8 +74,7 @@ func CreateTUN(name string) (ifce TUNDevice, err error) {
)
if errno != 0 {
- err = errno
- return nil, fmt.Errorf("error in unix.Syscall(unix.SYS_IOTL, ...): %v", err)
+ return nil, fmt.Errorf("_CTLIOCGINFO: %v", errno)
}
sc := sockaddrCtl{
@@ -105,148 +95,139 @@ func CreateTUN(name string) (ifce TUNDevice, err error) {
)
if errno != 0 {
- err = errno
- return nil, fmt.Errorf("error in unix.RawSyscall(unix.SYS_CONNECT, ...): %v", err)
+ return nil, fmt.Errorf("SYS_CONNECT: %v", errno)
}
- // read (new) name of interface
+ tun, err := CreateTUNFromFile(os.NewFile(uintptr(fd), ""))
- var ifName struct {
- name [16]byte
+ if err == nil && name == "utun" {
+ fmt.Printf("OS assigned interface: %s\n", tun.(*NativeTun).name)
}
- ifNameSize := uintptr(16)
- _, _, errno = unix.Syscall6(
- unix.SYS_GETSOCKOPT,
- uintptr(fd),
- 2, /* #define SYSPROTO_CONTROL 2 */
- 2, /* #define UTUN_OPT_IFNAME 2 */
- uintptr(unsafe.Pointer(&ifName)),
- uintptr(unsafe.Pointer(&ifNameSize)), 0)
+ return tun, err
+}
- if errno != 0 {
- err = errno
- return nil, fmt.Errorf("error in unix.Syscall6(unix.SYS_GETSOCKOPT, ...): %v", err)
- }
+func CreateTUNFromFile(file *os.File) (TUNDevice, error) {
- device := &NativeTUN{
- name: string(ifName.name[:ifNameSize-1 /* -1 is for \0 */]),
- f: os.NewFile(uintptr(fd), string(ifName.name[:])),
+ tun := &NativeTun{
+ fd: file,
mtu: 1500,
events: make(chan TUNEvent, 10),
errors: make(chan error, 1),
}
- // start listener
+ _, err := tun.Name()
+ if err != nil {
+ return nil, err
+ }
- go func(native *NativeTUN) {
- // TODO: Fix this very niave implementation
+ // TODO: Fix this very naive implementation
+ go func(tun *NativeTun) {
var (
statusUp bool
statusMTU int
)
for ; ; time.Sleep(time.Second) {
- intr, err := net.InterfaceByName(device.name)
+ intr, err := net.InterfaceByName(tun.name)
if err != nil {
- native.errors <- err
+ tun.errors <- err
return
}
// Up / Down event
up := (intr.Flags & net.FlagUp) != 0
if up != statusUp && up {
- native.events <- TUNEventUp
+ tun.events <- TUNEventUp
}
if up != statusUp && !up {
- native.events <- TUNEventDown
+ tun.events <- TUNEventDown
}
statusUp = up
// MTU changes
if intr.MTU != statusMTU {
- native.events <- TUNEventMTUUpdate
+ tun.events <- TUNEventMTUUpdate
}
statusMTU = intr.MTU
}
- }(device)
+ }(tun)
// set default MTU
+ err = tun.setMTU(DefaultMTU)
- err = device.setMTU(DefaultMTU)
-
- return device, err
+ return tun, err
}
-var _ io.ReadWriteCloser = (*NativeTUN)(nil)
+func (tun *NativeTun) Name() (string, error) {
-func (t *NativeTUN) Events() chan TUNEvent {
- return t.events
-}
+ var ifName struct {
+ name [16]byte
+ }
+ ifNameSize := uintptr(16)
-func (t *NativeTUN) Read(to []byte) (int, error) {
- t.rMu.Lock()
- defer t.rMu.Unlock()
+ _, _, errno := unix.Syscall6(
+ unix.SYS_GETSOCKOPT,
+ uintptr(tun.fd.Fd()),
+ 2, /* #define SYSPROTO_CONTROL 2 */
+ 2, /* #define UTUN_OPT_IFNAME 2 */
+ uintptr(unsafe.Pointer(&ifName)),
+ uintptr(unsafe.Pointer(&ifNameSize)), 0)
- if cap(t.rBuf) < len(to)+4 {
- t.rBuf = make([]byte, len(to)+4)
+ if errno != 0 {
+ return "", fmt.Errorf("SYS_GETSOCKOPT: %v", errno)
}
- t.rBuf = t.rBuf[:len(to)+4]
- n, err := t.f.Read(t.rBuf)
- copy(to, t.rBuf[4:])
- return n - 4, err
+ tun.name = string(ifName.name[:ifNameSize-1])
+ return tun.name, nil
}
-func (t *NativeTUN) Write(from []byte) (int, error) {
+func (tun *NativeTun) File() *os.File {
+ return tun.fd
+}
- if len(from) == 0 {
- return 0, unix.EIO
- }
+func (tun *NativeTun) Events() chan TUNEvent {
+ return tun.events
+}
- t.wMu.Lock()
- defer t.wMu.Unlock()
+func (tun *NativeTun) Read(buff []byte, offset int) (int, error) {
- if cap(t.wBuf) < len(from)+4 {
- t.wBuf = make([]byte, len(from)+4)
+ buff = buff[offset-4:]
+ n, err := tun.fd.Read(buff[:])
+ if n < 4 {
+ return 0, err
}
- t.wBuf = t.wBuf[:len(from)+4]
-
- // determine the IP Family for the NULL L2 Header
+ return n - 4, err
+}
- ipVer := from[0] >> 4
- if ipVer == ipv4.Version {
- t.wBuf[3] = unix.AF_INET
- } else if ipVer == ipv6.Version {
- t.wBuf[3] = unix.AF_INET6
- } else {
- return 0, errors.New("Unable to determine IP version from packet.")
- }
+func (tun *NativeTun) Write(buff []byte, offset int) (int, error) {
- copy(t.wBuf[4:], from)
+ // reserve space for header
- n, err := t.f.Write(t.wBuf)
- return n - 4, err
-}
+ buff = buff[offset-4:]
-func (t *NativeTUN) Close() error {
+ // add packet information header
- // lock to make sure no read/write is in process.
+ buff[0] = 0x00
+ buff[1] = 0x00
+ buff[2] = 0x00
- t.rMu.Lock()
- defer t.rMu.Unlock()
+ if buff[4]>>4 == ipv6.Version {
+ buff[3] = unix.AF_INET6
+ } else {
+ buff[3] = unix.AF_INET
+ }
- t.wMu.Lock()
- defer t.wMu.Unlock()
+ // write
- return t.f.Close()
+ return tun.fd.Write(buff)
}
-func (t *NativeTUN) Name() string {
- return t.name
+func (tun *NativeTun) Close() error {
+ return tun.fd.Close()
}
-func (t *NativeTUN) setMTU(n int) error {
+func (tun *NativeTun) setMTU(n int) error {
// open datagram socket
@@ -267,7 +248,7 @@ func (t *NativeTUN) setMTU(n int) error {
// do ioctl call
var ifr [32]byte
- copy(ifr[:], t.name)
+ copy(ifr[:], tun.name)
binary.LittleEndian.PutUint32(ifr[16:20], uint32(n))
_, _, errno := unix.Syscall(
unix.SYS_IOCTL,
@@ -277,13 +258,13 @@ func (t *NativeTUN) setMTU(n int) error {
)
if errno != 0 {
- return fmt.Errorf("Failed to set MTU on %s", t.name)
+ return fmt.Errorf("Failed to set MTU on %s", tun.name)
}
return nil
}
-func (t *NativeTUN) MTU() (int, error) {
+func (tun *NativeTun) MTU() (int, error) {
// open datagram socket
@@ -302,7 +283,7 @@ func (t *NativeTUN) MTU() (int, error) {
// do ioctl call
var ifr [64]byte
- copy(ifr[:], t.name)
+ copy(ifr[:], tun.name)
_, _, errno := unix.Syscall(
unix.SYS_IOCTL,
uintptr(fd),
@@ -310,7 +291,7 @@ func (t *NativeTUN) MTU() (int, error) {
uintptr(unsafe.Pointer(&ifr[0])),
)
if errno != 0 {
- return 0, fmt.Errorf("Failed to get MTU on %s", t.name)
+ return 0, fmt.Errorf("Failed to get MTU on %s", tun.name)
}
// convert result to signed 32-bit int
diff --git a/tun_linux.go b/tun_linux.go
index b0ffa00..a74a9cc 100644
--- a/tun_linux.go
+++ b/tun_linux.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
/* Copyright 2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved. */
package main
diff --git a/tun_windows.go b/tun_windows.go
index 0711032..c0c9ff8 100644
--- a/tun_windows.go
+++ b/tun_windows.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/uapi.go b/uapi.go
index 732bf82..c87a536 100644
--- a/uapi.go
+++ b/uapi.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/uapi_darwin.go b/uapi_darwin.go
index 2850184..69b0e3d 100644
--- a/uapi_darwin.go
+++ b/uapi_darwin.go
@@ -1,12 +1,17 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
+ "errors"
"fmt"
"golang.org/x/sys/unix"
"net"
"os"
"path"
- "time"
)
const (
@@ -22,6 +27,8 @@ type UAPIListener struct {
listener net.Listener // unix socket listener
connNew chan net.Conn
connErr chan error
+ kqueueFd int
+ keventFd int
}
func (l *UAPIListener) Accept() (net.Conn, error) {
@@ -37,48 +44,74 @@ func (l *UAPIListener) Accept() (net.Conn, error) {
}
func (l *UAPIListener) Close() error {
- return l.listener.Close()
+ err1 := unix.Close(l.kqueueFd)
+ err2 := unix.Close(l.keventFd)
+ err3 := l.listener.Close()
+ if err1 != nil {
+ return err1
+ }
+ if err2 != nil {
+ return err2
+ }
+ return err3
}
func (l *UAPIListener) Addr() net.Addr {
return nil
}
-func NewUAPIListener(name string) (net.Listener, error) {
+func UAPIListen(name string, file *os.File) (net.Listener, error) {
- // check if path exist
+ // wrap file in listener
- err := os.MkdirAll(socketDirectory, 077)
- if err != nil && !os.IsExist(err) {
+ listener, err := net.FileListener(file)
+ if err != nil {
return nil, err
}
- // open UNIX socket
+ uapi := &UAPIListener{
+ listener: listener,
+ connNew: make(chan net.Conn, 1),
+ connErr: make(chan error, 1),
+ }
socketPath := path.Join(
socketDirectory,
fmt.Sprintf(socketName, name),
)
- listener, err := net.Listen("unix", socketPath)
+ // watch for deletion of socket
+
+ uapi.kqueueFd, err = unix.Kqueue()
if err != nil {
return nil, err
}
-
- uapi := &UAPIListener{
- listener: listener,
- connNew: make(chan net.Conn, 1),
- connErr: make(chan error, 1),
+ uapi.keventFd, err = unix.Open(socketDirectory, unix.O_EVTONLY, 0)
+ if err != nil {
+ unix.Close(uapi.kqueueFd)
+ return nil, err
}
- // watch for deletion of socket
-
go func(l *UAPIListener) {
- for ; ; time.Sleep(time.Second) {
- if _, err := os.Stat(socketPath); os.IsNotExist(err) {
+ event := unix.Kevent_t{
+ Ident: uint64(uapi.keventFd),
+ Filter: unix.EVFILT_VNODE,
+ Flags: unix.EV_ADD | unix.EV_ENABLE | unix.EV_ONESHOT,
+ Fflags: unix.NOTE_WRITE,
+ }
+ events := make([]unix.Kevent_t, 1)
+ n := 1
+ var kerr error
+ for {
+ // start with lstat to avoid race condition
+ if _, err := os.Lstat(socketPath); os.IsNotExist(err) {
l.connErr <- err
return
}
+ if kerr != nil || n != 1 {
+ return
+ }
+ n, kerr = unix.Kevent(uapi.kqueueFd, []unix.Kevent_t{event}, events, nil)
}
}(uapi)
@@ -97,3 +130,56 @@ func NewUAPIListener(name string) (net.Listener, error) {
return uapi, nil
}
+
+func UAPIOpen(name string) (*os.File, error) {
+
+ // check if path exist
+
+ err := os.MkdirAll(socketDirectory, 0600)
+ if err != nil && !os.IsExist(err) {
+ return nil, err
+ }
+
+ // open UNIX socket
+
+ socketPath := path.Join(
+ socketDirectory,
+ fmt.Sprintf(socketName, name),
+ )
+
+ addr, err := net.ResolveUnixAddr("unix", socketPath)
+ if err != nil {
+ return nil, err
+ }
+
+ listener, err := func() (*net.UnixListener, error) {
+
+ // initial connection attempt
+
+ listener, err := net.ListenUnix("unix", addr)
+ if err == nil {
+ return listener, nil
+ }
+
+ // check if socket already active
+
+ _, err = net.Dial("unix", socketPath)
+ if err == nil {
+ return nil, errors.New("unix socket in use")
+ }
+
+ // cleanup & attempt again
+
+ err = os.Remove(socketPath)
+ if err != nil {
+ return nil, err
+ }
+ return net.ListenUnix("unix", addr)
+ }()
+
+ if err != nil {
+ return nil, err
+ }
+
+ return listener.File()
+}
diff --git a/uapi_linux.go b/uapi_linux.go
index f97a18a..c40472e 100644
--- a/uapi_linux.go
+++ b/uapi_linux.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
import (
diff --git a/uapi_windows.go b/uapi_windows.go
index 7807235..01f5505 100644
--- a/uapi_windows.go
+++ b/uapi_windows.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package main
/* UAPI on windows uses a bidirectional named pipe
diff --git a/xchacha20poly1305/xchacha20.go b/xchacha20poly1305/xchacha20.go
index a6e59f0..bd27f02 100644
--- a/xchacha20poly1305/xchacha20.go
+++ b/xchacha20poly1305/xchacha20.go
@@ -1,6 +1,8 @@
-// Copyright (c) 2016 Andreas Auernhammer. All rights reserved.
-// Use of this source code is governed by a license that can be
-// found in the LICENSE file.
+/* SPDX-License-Identifier: MIT
+ *
+ * Copyright (C) 2016 Andreas Auernhammer. All Rights Reserved.
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
package xchacha20poly1305
diff --git a/xchacha20poly1305/xchacha20_test.go b/xchacha20poly1305/xchacha20_test.go
index 5d5b78f..c0d11d7 100644
--- a/xchacha20poly1305/xchacha20_test.go
+++ b/xchacha20poly1305/xchacha20_test.go
@@ -1,3 +1,8 @@
+/* SPDX-License-Identifier: GPL-2.0
+ *
+ * Copyright (C) 2017-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
+ */
+
package xchacha20poly1305
import (