add comments

This commit is contained in:
netbyte 2022-06-14 00:14:21 +08:00
parent d3a5d1b7de
commit 321870d194
16 changed files with 81 additions and 12 deletions

View File

@ -6,8 +6,10 @@ import (
"github.com/patrickmn/go-cache"
)
// The global cache
var _cache = cache.New(30*time.Minute, 10*time.Minute)
// GetCache returns the cache
func GetCache() *cache.Cache {
return _cache
}

View File

@ -1,11 +1,14 @@
package cipher
// The default key
var _key = []byte("vtun@2022")
// SetKey sets the key
func SetKey(key string) {
_key = []byte(key)
}
// XOR encrypts the data
func XOR(src []byte) []byte {
_klen := len(_key)
for i := 0; i < len(src); i++ {

View File

@ -1,5 +1,6 @@
package config
// The config struct
type Config struct {
DeviceName string
LocalAddr string

View File

@ -2,21 +2,28 @@ package counter
import "sync/atomic"
// totalReadBytes is the total number of bytes read
var _totalReadBytes uint64 = 0
// totalWrittenBytes is the total number of bytes written
var _totalWrittenBytes uint64 = 0
// IncrReadBytes increments the number of bytes read
func IncrReadBytes(n int) {
atomic.AddUint64(&_totalReadBytes, uint64(n))
}
//IncrWrittenBytes increments the number of bytes written
func IncrWrittenBytes(n int) {
atomic.AddUint64(&_totalWrittenBytes, uint64(n))
}
// GetReadBytes returns the number of bytes read
func GetReadBytes() uint64 {
return _totalReadBytes
}
// GetWrittenBytes returns the number of bytes written
func GetWrittenBytes() uint64 {
return _totalWrittenBytes
}

View File

@ -15,6 +15,7 @@ import (
"github.com/net-byte/vtun/common/config"
)
// ConnectServer connects to the server with the given address.
func ConnectServer(config config.Config) net.Conn {
net.DefaultResolver = &net.Resolver{
PreferGo: true,
@ -47,6 +48,7 @@ func ConnectServer(config config.Config) net.Conn {
return c
}
// GetInterfaceName returns the name of interface
func GetInterface() (name string) {
ifaces := getAllInterfaces()
if len(ifaces) == 0 {
@ -63,6 +65,7 @@ func GetInterface() (name string) {
return name
}
// getAllInterfaces returns all interfaces
func getAllInterfaces() []net.Interface {
ifaces, err := net.Interfaces()
if err != nil {
@ -82,6 +85,7 @@ func getAllInterfaces() []net.Interface {
return outInterfaces
}
// isPhysicalInterface returns true if the interface is physical
func isPhysicalInterface(addr string) bool {
prefixArray := []string{"ens", "enp", "enx", "eno", "eth", "en0", "wlan", "wlp", "wlo", "wlx", "wifi0", "lan0"}
for _, pref := range prefixArray {
@ -92,6 +96,7 @@ func isPhysicalInterface(addr string) bool {
return false
}
// Lookup IP address of the given hostname
func LookupIP(domain string) net.IP {
ips, err := net.LookupIP(domain)
if err != nil || len(ips) == 0 {
@ -101,32 +106,39 @@ func LookupIP(domain string) net.IP {
return ips[0]
}
// IsIPv4 returns true if the packet is IPv4s
func IsIPv4(packet []byte) bool {
flag := packet[0] >> 4
return flag == 4
}
// IsIPv6 returns true if the packet is IPv6s
func IsIPv6(packet []byte) bool {
flag := packet[0] >> 4
return flag == 6
}
// GetIPv4Src returns the IPv4 source address of the packet
func GetIPv4Src(packet []byte) net.IP {
return net.IPv4(packet[12], packet[13], packet[14], packet[15])
}
// GEtIPv4Dst returns the IPv4 destination address of the packet
func GetIPv4Dst(packet []byte) net.IP {
return net.IPv4(packet[16], packet[17], packet[18], packet[19])
}
// GetIPv6Src returns the IPv6 source address of the packet
func GetIPv6Src(packet []byte) net.IP {
return net.IP(packet[8:24])
}
// GetIPv6Dst returns the IPv6 destination address of the packet
func GetIPv6Dst(packet []byte) net.IP {
return net.IP(packet[24:40])
}
// GetSrcKey returns the source key of the packet
func GetSrcKey(packet []byte) string {
key := ""
if IsIPv4(packet) && len(packet) >= 20 {
@ -137,6 +149,7 @@ func GetSrcKey(packet []byte) string {
return key
}
// GetdstKey returns the destination key of the packets
func GetDstKey(packet []byte) string {
key := ""
if IsIPv4(packet) && len(packet) >= 20 {
@ -147,6 +160,7 @@ func GetDstKey(packet []byte) string {
return key
}
// ExecuteCommand executes the given command
func ExecCmd(c string, args ...string) string {
log.Printf("exec cmd: %v %v:", c, args)
cmd := exec.Command(c, args...)
@ -161,6 +175,7 @@ func ExecCmd(c string, args ...string) string {
return strings.ReplaceAll(s, "\n", "")
}
// GetLocalGatewayOnLinux returns the local gateway IP address on Linux
func GetLocalGatewayOnLinux(ipv4 bool) string {
if ipv4 {
return ExecCmd("sh", "-c", "route -n | grep 'UG[ \t]' | awk 'NR==1{print $2}'")
@ -168,6 +183,7 @@ func GetLocalGatewayOnLinux(ipv4 bool) string {
return ExecCmd("sh", "-c", "route -6 -n | grep 'UG[ \t]' | awk 'NR==1{print $2}'")
}
// GetLocalGatewayOnMac returns the local gateway IP address on MacOS
func GetLocalGatewayOnMac(ipv4 bool) string {
if ipv4 {
return ExecCmd("sh", "-c", "route -n get default | grep 'gateway' | awk 'NR==1{print $2}'")

View File

@ -17,6 +17,7 @@ import (
"github.com/songgao/water"
)
// StartClient starts the grpc client
func StartClient(config config.Config) {
log.Printf("vtun grpc client started on %v", config.LocalAddr)
iface := tun.CreateTun(config)
@ -47,6 +48,7 @@ func StartClient(config config.Config) {
}
}
// tunToGrpc sends packets from tun to grpc
func tunToGrpc(config config.Config, iface *water.Interface) {
packet := make([]byte, config.MTU)
for {
@ -68,6 +70,7 @@ func tunToGrpc(config config.Config, iface *water.Interface) {
}
}
// grpcToTun sends packets from grpc to tun
func grpcToTun(config config.Config, stream proto.GrpcServe_TunnelClient, iface *water.Interface) {
for {
packet, err := stream.Recv()

View File

@ -17,17 +17,20 @@ import (
"github.com/songgao/water"
)
// The StreamService is the implementation of the StreamServer interface
type StreamService struct {
proto.UnimplementedGrpcServeServer
config config.Config
iface *water.Interface
}
// Tunnel implements the StreamServer interface
func (s *StreamService) Tunnel(srv proto.GrpcServe_TunnelServer) error {
toServer(srv, s.config, s.iface)
return nil
}
// StartServer starts the grpc server
func StartServer(config config.Config) {
log.Printf("vtun grpc server started on %v", config.LocalAddr)
iface := tun.CreateTun(config)
@ -49,6 +52,7 @@ func StartServer(config config.Config) {
}
}
// toClient sends packets from tun to grpc
func toClient(config config.Config, iface *water.Interface) {
packet := make([]byte, config.MTU)
for {
@ -68,6 +72,7 @@ func toClient(config config.Config, iface *water.Interface) {
}
}
// toServer sends packets from grpc to tun
func toServer(srv proto.GrpcServe_TunnelServer, config config.Config, iface *water.Interface) {
for {
packet, err := srv.Recv()

View File

@ -52,6 +52,7 @@ func main() {
stopApp(config)
}
// initConfig initializes the config
func initConfig(config *config.Config) {
if !config.ServerMode && config.GlobalMode {
host, _, err := net.SplitHostPort(config.ServerAddr)
@ -71,6 +72,7 @@ func initConfig(config *config.Config) {
log.Printf("init config:%s", string(json))
}
// startApp starts the app
func startApp(config config.Config) {
switch config.Protocol {
case "udp":
@ -106,7 +108,8 @@ func startApp(config config.Config) {
}
}
// stopApp stops the app
func stopApp(config config.Config) {
tun.Reset(config)
log.Printf("stopped!!!")
tun.ResetTun(config)
log.Printf("vtun stopped")
}

View File

@ -9,25 +9,30 @@ import (
"github.com/patrickmn/go-cache"
)
// The global cache for register
var _register *cache.Cache
func init() {
_register = cache.New(30*time.Minute, 3*time.Minute)
}
// AddClientIP adds a client ip to the register
func AddClientIP(ip string) {
_register.Add(ip, 0, cache.DefaultExpiration)
}
// DeleteClientIP deletes a client ip from the register
func DeleteClientIP(ip string) {
_register.Delete(ip)
}
// ExistClientIP checks if the client ip is in the register
func ExistClientIP(ip string) bool {
_, ok := _register.Get(ip)
return ok
}
// keepAlive keeps the client ip alive
func KeepAliveClientIP(ip string) {
if ExistClientIP(ip) {
_register.Increment(ip, 1)
@ -36,6 +41,7 @@ func KeepAliveClientIP(ip string) {
}
}
// PickClientIP picks a client ip from the register
func PickClientIP(cidr string) (clientIP string, prefixLength string) {
ip, ipNet, err := net.ParseCIDR(cidr)
if err != nil {
@ -59,7 +65,8 @@ func PickClientIP(cidr string) (clientIP string, prefixLength string) {
return "", ""
}
func ListClientIP() []string {
// ListClientIPs returns the client ips in the register
func ListClientIPs() []string {
result := []string{}
for k := range _register.Items() {
result = append(result, k)
@ -67,11 +74,13 @@ func ListClientIP() []string {
return result
}
// addressCount returns the number of addresses in a CIDR network.
func addressCount(network *net.IPNet) uint64 {
prefixLen, bits := network.Mask.Size()
return 1 << (uint64(bits) - uint64(prefixLen))
}
// incr increments the ip by 1
func incr(IP net.IP) net.IP {
IP = checkIPv4(IP)
incIP := make([]byte, len(IP))
@ -85,6 +94,7 @@ func incr(IP net.IP) net.IP {
return incIP
}
// checkIPv4 checks if the ip is IPv4
func checkIPv4(ip net.IP) net.IP {
if v4 := ip.To4(); v4 != nil {
return v4

View File

@ -14,7 +14,7 @@ import (
"github.com/songgao/water"
)
// Start tls client
// StartClient starts the tls client
func StartClient(config config.Config) {
log.Printf("vtun tls client started on %v", config.LocalAddr)
iface := tun.CreateTun(config)
@ -37,6 +37,7 @@ func StartClient(config config.Config) {
}
}
// tunToTLS sends packets from tun to tls
func tunToTLS(config config.Config, iface *water.Interface) {
packet := make([]byte, config.MTU)
for {
@ -59,6 +60,7 @@ func tunToTLS(config config.Config, iface *water.Interface) {
}
}
// tlsToTun sends packets from tls to tun
func tlsToTun(config config.Config, tlsconn net.Conn, iface *water.Interface) {
defer tlsconn.Close()
packet := make([]byte, config.MTU)

View File

@ -15,7 +15,7 @@ import (
"github.com/songgao/water"
)
//Start tls server
// StartServer starts the tls server
func StartServer(config config.Config) {
log.Printf("vtun tls server started on %v", config.LocalAddr)
iface := tun.CreateTun(config)
@ -51,6 +51,7 @@ func StartServer(config config.Config) {
}
}
// toClient sends packets from iface to tlsconn
func toClient(config config.Config, iface *water.Interface) {
packet := make([]byte, config.MTU)
for {
@ -70,7 +71,7 @@ func toClient(config config.Config, iface *water.Interface) {
}
}
// todo fallback to http
// toServer sends packets from tlsconn to iface
func toServer(config config.Config, tlsconn net.Conn, iface *water.Interface) {
defer tlsconn.Close()
packet := make([]byte, config.MTU)

View File

@ -11,6 +11,7 @@ import (
"github.com/songgao/water"
)
// CreateTun creates a tun interface
func CreateTun(config config.Config) (iface *water.Interface) {
c := water.Config{DeviceType: water.TUN}
if config.DeviceName != "" {
@ -25,6 +26,7 @@ func CreateTun(config config.Config) (iface *water.Interface) {
return iface
}
// ConfigTun configures the tun interface
func configTun(config config.Config, iface *water.Interface) {
os := runtime.GOOS
ip, _, err := net.ParseCIDR(config.CIDR)
@ -91,7 +93,8 @@ func configTun(config config.Config, iface *water.Interface) {
}
}
func Reset(config config.Config) {
// ResetTun resets the tun interface
func ResetTun(config config.Config) {
os := runtime.GOOS
if os == "darwin" && !config.ServerMode && config.GlobalMode {
netutil.ExecCmd("route", "add", "default", config.LocalGateway)

View File

@ -12,7 +12,7 @@ import (
"golang.org/x/net/ipv6"
)
// Start udp client
// StartClient starts the udp client
func StartClient(config config.Config) {
log.Printf("vtun udp client started on %v", config.LocalAddr)
iface := tun.CreateTun(config)
@ -45,6 +45,7 @@ func StartClient(config config.Config) {
c.tunToUdp()
}
// The client struct
type Client struct {
config config.Config
iface *water.Interface
@ -52,6 +53,7 @@ type Client struct {
serverAddr *net.UDPAddr
}
// udpToTun sends packets from udp to tun
func (c *Client) udpToTun() {
packet := make([]byte, c.config.MTU)
for {
@ -66,6 +68,8 @@ func (c *Client) udpToTun() {
c.iface.Write(b)
}
}
// tunToUdp sends packets from tun to udp
func (c *Client) tunToUdp() {
packet := make([]byte, c.config.MTU)
for {

View File

@ -15,7 +15,7 @@ import (
"golang.org/x/net/ipv6"
)
// Start udp server
// StartServer starts the udp server
func StartServer(config config.Config) {
log.Printf("vtun udp server started on %v", config.LocalAddr)
iface := tun.CreateTun(config)
@ -44,6 +44,7 @@ func StartServer(config config.Config) {
s.udpToTun()
}
// the server struct
type Server struct {
config config.Config
iface *water.Interface
@ -51,6 +52,7 @@ type Server struct {
connCache *cache.Cache
}
// tunToUdp sends packets from tun to udp
func (s *Server) tunToUdp() {
packet := make([]byte, s.config.MTU)
for {
@ -70,6 +72,7 @@ func (s *Server) tunToUdp() {
}
}
// udpToTun sends packets from udp to tun
func (s *Server) udpToTun() {
packet := make([]byte, s.config.MTU)
for {

View File

@ -14,7 +14,7 @@ import (
"github.com/songgao/water"
)
// Start websocket client
// StartClient starts the ws client
func StartClient(config config.Config) {
log.Printf("vtun websocket client started on %v", config.LocalAddr)
iface := tun.CreateTun(config)
@ -31,6 +31,7 @@ func StartClient(config config.Config) {
}
}
// wsToTun sends packets from ws to tun
func wsToTun(config config.Config, wsconn net.Conn, iface *water.Interface) {
defer wsconn.Close()
for {
@ -49,6 +50,7 @@ func wsToTun(config config.Config, wsconn net.Conn, iface *water.Interface) {
}
}
// tunToWs sends packets from tun to ws
func tunToWs(config config.Config, iface *water.Interface) {
packet := make([]byte, config.MTU)
for {

View File

@ -22,7 +22,7 @@ import (
"github.com/songgao/water"
)
// Start websocket server
// StartServer starts the ws server
func StartServer(config config.Config) {
iface := tun.CreateTun(config)
// server -> client
@ -88,7 +88,7 @@ func StartServer(config config.Config) {
if !checkPermission(w, r, config) {
return
}
io.WriteString(w, strings.Join(register.ListClientIP(), "\r\n"))
io.WriteString(w, strings.Join(register.ListClientIPs(), "\r\n"))
})
http.HandleFunc("/register/prefix/ipv4", func(w http.ResponseWriter, r *http.Request) {
@ -132,6 +132,8 @@ func StartServer(config config.Config) {
}
}
// checkPermission checks the permission of the request
func checkPermission(w http.ResponseWriter, req *http.Request, config config.Config) bool {
key := req.Header.Get("key")
if key != config.Key {
@ -142,6 +144,7 @@ func checkPermission(w http.ResponseWriter, req *http.Request, config config.Con
return true
}
// toClient sends data to client
func toClient(config config.Config, iface *water.Interface) {
packet := make([]byte, config.MTU)
for {
@ -162,6 +165,7 @@ func toClient(config config.Config, iface *water.Interface) {
}
}
// toServer sends data to server
func toServer(config config.Config, wsconn net.Conn, iface *water.Interface) {
defer wsconn.Close()
for {