From e8575286bb20fc46218c82822d7e54e7851d30f3 Mon Sep 17 00:00:00 2001 From: Ruben Pollan Date: Wed, 18 Jul 2018 20:24:31 +0200 Subject: [feat] add fixed openvpn args and parse the client ones --- helper/args.go | 104 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ helper/darwin.go | 17 ++++++--- helper/helper.go | 3 +- helper/linux.go | 8 ++++- helper/windows.go | 11 ++++-- 5 files changed, 135 insertions(+), 8 deletions(-) create mode 100644 helper/args.go diff --git a/helper/args.go b/helper/args.go new file mode 100644 index 0000000..5651cb4 --- /dev/null +++ b/helper/args.go @@ -0,0 +1,104 @@ +package main + +import ( + "log" + "net" + "os" + "regexp" + "strconv" +) + +const ( + openvpnUser = "nobody" + openvpnGroup = "nobody" + nameserver = "10.42.0.1" +) + +var ( + fixedArgs = []string{ + "--nobind", + "--client", + "--dev", "tun", + "--tls-client", + "--remote-cert-tls", "server", + "--dhcp-option", "DNS", nameserver, + "--user", openvpnUser, + "--group", openvpnGroup, + "--log", logFolder + "openvpn.log", + } + + allowendArgs = map[string][]string{ + "--remote": []string{"IP", "NUMBER", "PROTO"}, + "--tls-cipher": []string{"CIPHER"}, + "--cipher": []string{"CIPHER"}, + "--auth": []string{"CIPHER"}, + "--management-client": []string{}, + "--management": []string{"IP", "NUMBER"}, + "--cert": []string{"FILE"}, + "--key": []string{"FILE"}, + "--ca": []string{"FILE"}, + "--fragment": []string{"NUMBER"}, + "--keepalive": []string{"NUMBER", "NUMBER"}, + "--verb": []string{"NUMBER"}, + "--tun-ipv6": []string{}, + } + + cipher = regexp.MustCompile("^[A-Z0-9-]+$") + formats = map[string]func(s string) bool{ + "NUMBER": isNumber, + "PROTO": isProto, + "IP": isIP, + "CIPHER": cipher.MatchString, + "FILE": isFile, + } +) + +func parseOpenvpnArgs(args []string) []string { + newArgs := fixedArgs + for i := 0; i < len(args); i++ { + params, ok := allowendArgs[args[i]] + if !ok { + log.Printf("Invalid openvpn arg: %s", args[i]) + continue + } + for j, arg := range args[i+1 : i+len(params)+1] { + if !formats[params[j]](arg) { + ok = false + break + } + } + if ok { + newArgs = append(newArgs, args[i:i+len(params)+1]...) + i = i + len(params) + } else { + log.Printf("Invalid openvpn arg params: %v", args[i:i+len(params)+1]) + } + } + return newArgs +} + +func isNumber(s string) bool { + _, err := strconv.Atoi(s) + return err == nil +} + +func isProto(s string) bool { + for _, proto := range []string{"tcp", "udp", "tcp4", "udp4", "tcp6", "udp6"} { + if s == proto { + return true + } + } + return false +} + +func isIP(s string) bool { + return net.ParseIP(s) != nil +} + +func isFile(s string) bool { + info, err := os.Stat(s) + if err != nil { + return false + } + return !info.IsDir() +} diff --git a/helper/darwin.go b/helper/darwin.go index 33a69fc..34af01e 100644 --- a/helper/darwin.go +++ b/helper/darwin.go @@ -39,17 +39,26 @@ import ( ) const ( - logPath = "/Applications/RiseupVPN.app/Contents/helper/helper.log" - openvpnPath = "/Applications/RiseupVPN.app/Contents/Resources/openvpn.leap" + appPath = "/Applications/RiseupVPN.app/" + helperPath = appPath + "Contents/helper/" + logFolder = helperPath + openvpnPath = appPath + "Contents/Resources/openvpn.leap" - rulefilePath = "/Applications/RiseupVPN.app/Contents/helper/bitmask.pf.conf" + rulefilePath = helperPath + "bitmask.pf.conf" bitmask_anchor = "com.apple/250.BitmaskFirewall" gateways_table = "bitmask_gateways" - nameserver = "10.42.0.1" pfctl = "/sbin/pfctl" ) +var ( + platformOpenvpnFlags = []string{ + "--script-security", "2", + "--up", helperPath + "client.up.sh", + "--down", helperPath + "client.down.sh", + } +) + func daemonize() { cntxt := &daemon.Context{ PidFileName: "pid", diff --git a/helper/helper.go b/helper/helper.go index 9f09e81..9d6d327 100644 --- a/helper/helper.go +++ b/helper/helper.go @@ -63,6 +63,7 @@ func (openvpn *openvpnT) start(w http.ResponseWriter, r *http.Request) { return } + args = parseOpenvpnArgs(args) log.Printf("start openvpn: %v", args) err = openvpn.run(args) if err != nil { @@ -145,7 +146,7 @@ func getArgs(r *http.Request) ([]string, error) { } func configureLogger() (io.Closer, error) { - logFile, err := os.OpenFile(logPath, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0666) + logFile, err := os.OpenFile(logFolder+"helper.log", os.O_RDWR|os.O_CREATE|os.O_APPEND, 0666) if err == nil { log.SetOutput(io.MultiWriter(logFile, os.Stderr)) } diff --git a/helper/linux.go b/helper/linux.go index f21cc55..3817989 100644 --- a/helper/linux.go +++ b/helper/linux.go @@ -23,11 +23,17 @@ import ( ) const ( - logPath = "/var/log/riseupvpn-helper.log" + logFolder = "/var/log/" systemOpenvpnPath = "/usr/sbin/openvpn" snapOpenvpnPath = "/snap/bin/riseup-vpn.openvpn" ) +var ( + platformOpenvpnFlags = []string{ + "--script-security", "1", + } +) + func daemonize() {} func getOpenvpnPath() string { diff --git a/helper/windows.go b/helper/windows.go index 61096c2..88c96e9 100644 --- a/helper/windows.go +++ b/helper/windows.go @@ -23,11 +23,18 @@ import ( ) const ( - logPath = `C:\Program Files\RiseupVPN\helper.log` - openvpnPath = `C:\Program Files\RiseupVPN\openvpn.exe` + appPath = `C:\Program Files\RiseupVPN\` + logFolder = appPath + openvpnPath = appPath + `openvpn.exe` chocoOpenvpnPath = `C:\Program Files\OpenVPN\bin\openvpn.exe` ) +var ( + platformOpenvpnFlags = []string{ + "--script-security", "1", + } +) + func daemonize() {} func getOpenvpnPath() string { -- cgit v1.2.3