mirror of
https://github.com/gravitl/netmaker.git
synced 2025-11-08 07:41:41 +08:00
connect to ext client by using handshake packet info
This commit is contained in:
parent
46d63d19a3
commit
d0d9bc5ecd
9 changed files with 470 additions and 182 deletions
|
|
@ -15,6 +15,8 @@ var IsHostNetwork bool
|
|||
var IsRelay bool
|
||||
var IsIngressGateway bool
|
||||
var IsRelayed bool
|
||||
var IsServer bool
|
||||
var InterfaceName string
|
||||
|
||||
const (
|
||||
NmProxyPort = 51722
|
||||
|
|
@ -74,8 +76,8 @@ type RemotePeer struct {
|
|||
}
|
||||
|
||||
type ExtClientPeer struct {
|
||||
Endpoint *net.UDPAddr
|
||||
context.CancelFunc
|
||||
CancelFunc context.CancelFunc
|
||||
CommChan chan *net.UDPAddr
|
||||
}
|
||||
|
||||
type WgIfaceConf struct {
|
||||
|
|
@ -93,6 +95,8 @@ var RelayPeerMap = make(map[string]map[string]RemotePeer)
|
|||
|
||||
var ExtClientsWaitTh = make(map[string]ExtClientPeer)
|
||||
|
||||
var ExtSourceIpMap = make(map[string]RemotePeer)
|
||||
|
||||
// RunCmd - runs a local command
|
||||
func RunCmd(command string, printerr bool) (string, error) {
|
||||
args := strings.Fields(command)
|
||||
|
|
|
|||
|
|
@ -9,7 +9,6 @@ import (
|
|||
"net"
|
||||
"reflect"
|
||||
"runtime"
|
||||
"time"
|
||||
|
||||
"github.com/gravitl/netmaker/nm-proxy/common"
|
||||
peerpkg "github.com/gravitl/netmaker/nm-proxy/peer"
|
||||
|
|
@ -163,6 +162,7 @@ func (m *ManagerAction) processPayload() (*wg.WGIface, error) {
|
|||
log.Println("failed to get real iface: ", err)
|
||||
}
|
||||
}
|
||||
common.InterfaceName = m.Payload.InterfaceName
|
||||
wgIface, err = wg.NewWGIFace(m.Payload.InterfaceName, "127.0.0.1/32", wg.DefaultMTU)
|
||||
if err != nil {
|
||||
log.Println("Failed init new interface: ", err)
|
||||
|
|
@ -179,6 +179,7 @@ func (m *ManagerAction) processPayload() (*wg.WGIface, error) {
|
|||
log.Println("falied to update peer: ", err)
|
||||
}
|
||||
m.Payload.Peers = append(m.Payload.Peers[:i], m.Payload.Peers[i+1:]...)
|
||||
continue
|
||||
}
|
||||
if m.Payload.PeerMap[m.Payload.Peers[i].PublicKey.String()].IsAttachedExtClient {
|
||||
if err := wgIface.Update(m.Payload.Peers[i], false); err != nil {
|
||||
|
|
@ -220,7 +221,7 @@ func (m *ManagerAction) processPayload() (*wg.WGIface, error) {
|
|||
m.Payload.Peers = append(m.Payload.Peers[:i], m.Payload.Peers[i+1:]...)
|
||||
|
||||
}
|
||||
log.Println("----> Skip Processing ExtClient: ", m.Payload.Peers[i].PublicKey.String())
|
||||
|
||||
continue
|
||||
}
|
||||
// check if proxy is off for the peer
|
||||
|
|
@ -384,12 +385,11 @@ func (m *ManagerAction) AddInterfaceToProxy() error {
|
|||
shouldProceed = true
|
||||
}
|
||||
if peerConf.IsExtClient && peerConf.IsAttachedExtClient && shouldProceed {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
common.ExtClientsWaitTh[peerI.PublicKey.String()] = common.ExtClientPeer{
|
||||
Endpoint: peerI.Endpoint,
|
||||
CancelFunc: cancel,
|
||||
}
|
||||
go proxy.StartSniffer(ctx, wgInterface.Name, m.Payload.WgAddr, peerConf.Address, wgInterface.Port)
|
||||
// ctx, cancel := context.WithCancel(context.Background())
|
||||
// common.ExtClientsWaitTh[peerI.PublicKey.String()] = common.ExtClientPeer{
|
||||
// CancelFunc: cancel,
|
||||
// }
|
||||
//go proxy.StartSniffer(ctx, wgInterface.Name, m.Payload.WgAddr, peerConf.Address, wgInterface.Port)
|
||||
}
|
||||
|
||||
if peerConf.IsExtClient && !peerConf.IsAttachedExtClient {
|
||||
|
|
@ -422,15 +422,16 @@ func (m *ManagerAction) AddInterfaceToProxy() error {
|
|||
go func(wgInterface *wg.WGIface, peer *wgtypes.PeerConfig,
|
||||
isRelayed bool, relayTo *net.UDPAddr, peerConf PeerConf, ingGwAddr string) {
|
||||
addExtClient := false
|
||||
commChan := make(chan *net.UDPAddr, 100)
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
common.ExtClientsWaitTh[peerI.PublicKey.String()] = common.ExtClientPeer{
|
||||
Endpoint: peer.Endpoint,
|
||||
CancelFunc: cancel,
|
||||
CommChan: commChan,
|
||||
}
|
||||
defer func() {
|
||||
if addExtClient {
|
||||
log.Println("GOT ENDPOINT for Extclient adding peer...")
|
||||
go proxy.StartSniffer(ctx, wgInterface.Name, ingGwAddr, peerConf.Address, wgInterface.Port)
|
||||
//go proxy.StartSniffer(ctx, wgInterface.Name, ingGwAddr, peerConf.Address, wgInterface.Port)
|
||||
common.PeerKeyHashMap[fmt.Sprintf("%x", md5.Sum([]byte(peer.PublicKey.String())))] = common.RemotePeer{
|
||||
Interface: wgInterface.Name,
|
||||
PeerKey: peer.PublicKey.String(),
|
||||
|
|
@ -438,30 +439,31 @@ func (m *ManagerAction) AddInterfaceToProxy() error {
|
|||
IsAttachedExtClient: peerConf.IsAttachedExtClient,
|
||||
Endpoint: peer.Endpoint,
|
||||
}
|
||||
common.ExtSourceIpMap[peer.Endpoint.String()] = common.RemotePeer{
|
||||
Interface: wgInterface.Name,
|
||||
PeerKey: peer.PublicKey.String(),
|
||||
IsExtClient: peerConf.IsExtClient,
|
||||
IsAttachedExtClient: peerConf.IsAttachedExtClient,
|
||||
Endpoint: peer.Endpoint,
|
||||
}
|
||||
|
||||
peerpkg.AddNewPeer(wgInterface, peer, peerConf.Address, isRelayed,
|
||||
peerConf.IsExtClient, peerConf.IsAttachedExtClient, relayedTo)
|
||||
|
||||
}
|
||||
log.Println("Exiting extclient watch Thread for: ", peer.PublicKey.String())
|
||||
}()
|
||||
for {
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
log.Println("Exiting extclient watch Thread for: ", wgInterface.Device.PublicKey.String())
|
||||
return
|
||||
default:
|
||||
wgInterface, err := wg.NewWGIFace(m.Payload.InterfaceName, "127.0.0.1/32", wg.DefaultMTU)
|
||||
if err != nil {
|
||||
log.Println("Failed init new interface: ", err)
|
||||
case endpoint := <-commChan:
|
||||
if endpoint != nil {
|
||||
addExtClient = true
|
||||
peer.Endpoint = endpoint
|
||||
delete(common.ExtClientsWaitTh, peer.PublicKey.String())
|
||||
return
|
||||
}
|
||||
for _, devpeerI := range wgInterface.Device.Peers {
|
||||
if devpeerI.PublicKey.String() == peer.PublicKey.String() && devpeerI.Endpoint != nil {
|
||||
peer.Endpoint = devpeerI.Endpoint
|
||||
addExtClient = true
|
||||
return
|
||||
}
|
||||
}
|
||||
time.Sleep(time.Second * 5)
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -21,7 +21,6 @@ import (
|
|||
func Start(ctx context.Context, mgmChan chan *manager.ManagerAction, apiServerAddr string) {
|
||||
log.Println("Starting Proxy...")
|
||||
common.IsHostNetwork = (os.Getenv("HOST_NETWORK") == "" || os.Getenv("HOST_NETWORK") == "on")
|
||||
|
||||
hInfo := stun.GetHostInfo(apiServerAddr)
|
||||
stun.Host = hInfo
|
||||
log.Printf("HOSTINFO: %+v", hInfo)
|
||||
|
|
|
|||
247
nm-proxy/packet/packet_helper.go
Normal file
247
nm-proxy/packet/packet_helper.go
Normal file
|
|
@ -0,0 +1,247 @@
|
|||
package packet
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"crypto/hmac"
|
||||
"crypto/subtle"
|
||||
"encoding/base64"
|
||||
"encoding/binary"
|
||||
"encoding/hex"
|
||||
"errors"
|
||||
"hash"
|
||||
"log"
|
||||
|
||||
"github.com/gravitl/netmaker/nm-proxy/wg"
|
||||
"golang.org/x/crypto/blake2s"
|
||||
"golang.org/x/crypto/chacha20poly1305"
|
||||
"golang.org/x/crypto/curve25519"
|
||||
"golang.org/x/crypto/poly1305"
|
||||
"golang.zx2c4.com/wireguard/tai64n"
|
||||
)
|
||||
|
||||
func init() {
|
||||
InitialChainKey = blake2s.Sum256([]byte(NoiseConstruction))
|
||||
mixHash(&InitialHash, &InitialChainKey, []byte(WGIdentifier))
|
||||
}
|
||||
func mixKey(dst, c *[blake2s.Size]byte, data []byte) {
|
||||
KDF1(dst, c[:], data)
|
||||
}
|
||||
|
||||
func mixHash(dst, h *[blake2s.Size]byte, data []byte) {
|
||||
hash, _ := blake2s.New256(nil)
|
||||
hash.Write(h[:])
|
||||
hash.Write(data)
|
||||
hash.Sum(dst[:0])
|
||||
hash.Reset()
|
||||
}
|
||||
func HMAC1(sum *[blake2s.Size]byte, key, in0 []byte) {
|
||||
mac := hmac.New(func() hash.Hash {
|
||||
h, _ := blake2s.New256(nil)
|
||||
return h
|
||||
}, key)
|
||||
mac.Write(in0)
|
||||
mac.Sum(sum[:0])
|
||||
}
|
||||
|
||||
func HMAC2(sum *[blake2s.Size]byte, key, in0, in1 []byte) {
|
||||
mac := hmac.New(func() hash.Hash {
|
||||
h, _ := blake2s.New256(nil)
|
||||
return h
|
||||
}, key)
|
||||
mac.Write(in0)
|
||||
mac.Write(in1)
|
||||
mac.Sum(sum[:0])
|
||||
}
|
||||
|
||||
func KDF1(t0 *[blake2s.Size]byte, key, input []byte) {
|
||||
HMAC1(t0, key, input)
|
||||
HMAC1(t0, t0[:], []byte{0x1})
|
||||
}
|
||||
|
||||
const (
|
||||
NoiseConstruction = "Noise_IKpsk2_25519_ChaChaPoly_BLAKE2s"
|
||||
WGIdentifier = "WireGuard v1 zx2c4 Jason@zx2c4.com"
|
||||
WGLabelMAC1 = "mac1----"
|
||||
WGLabelCookie = "cookie--"
|
||||
)
|
||||
|
||||
const (
|
||||
MessageInitiationType = 1
|
||||
MessageResponseType = 2
|
||||
MessageCookieReplyType = 3
|
||||
MessageTransportType = 4
|
||||
)
|
||||
const (
|
||||
NoisePublicKeySize = 32
|
||||
NoisePrivateKeySize = 32
|
||||
NoisePresharedKeySize = 32
|
||||
)
|
||||
|
||||
type (
|
||||
NoisePublicKey [NoisePublicKeySize]byte
|
||||
NoisePrivateKey [NoisePrivateKeySize]byte
|
||||
NoisePresharedKey [NoisePresharedKeySize]byte
|
||||
NoiseNonce uint64 // padded to 12-bytes
|
||||
)
|
||||
|
||||
type MessageInitiation struct {
|
||||
Type uint32
|
||||
Sender uint32
|
||||
Ephemeral NoisePublicKey
|
||||
Static [NoisePublicKeySize + poly1305.TagSize]byte
|
||||
Timestamp [tai64n.TimestampSize + poly1305.TagSize]byte
|
||||
MAC1 [blake2s.Size128]byte
|
||||
MAC2 [blake2s.Size128]byte
|
||||
}
|
||||
|
||||
var (
|
||||
InitialChainKey [blake2s.Size]byte
|
||||
InitialHash [blake2s.Size]byte
|
||||
ZeroNonce [chacha20poly1305.NonceSize]byte
|
||||
)
|
||||
|
||||
func KDF2(t0, t1 *[blake2s.Size]byte, key, input []byte) {
|
||||
var prk [blake2s.Size]byte
|
||||
HMAC1(&prk, key, input)
|
||||
HMAC1(t0, prk[:], []byte{0x1})
|
||||
HMAC2(t1, prk[:], t0[:], []byte{0x2})
|
||||
setZero(prk[:])
|
||||
}
|
||||
func setZero(arr []byte) {
|
||||
for i := range arr {
|
||||
arr[i] = 0
|
||||
}
|
||||
}
|
||||
func isZero(val []byte) bool {
|
||||
acc := 1
|
||||
for _, b := range val {
|
||||
acc &= subtle.ConstantTimeByteEq(b, 0)
|
||||
}
|
||||
return acc == 1
|
||||
}
|
||||
func uapiCfg(cfg ...string) string {
|
||||
if len(cfg)%2 != 0 {
|
||||
panic("odd number of args to uapiReader")
|
||||
}
|
||||
buf := new(bytes.Buffer)
|
||||
for i, s := range cfg {
|
||||
buf.WriteString(s)
|
||||
sep := byte('\n')
|
||||
if i%2 == 0 {
|
||||
sep = '='
|
||||
}
|
||||
buf.WriteByte(sep)
|
||||
}
|
||||
return buf.String()
|
||||
}
|
||||
func sharedSecret(sk *NoisePrivateKey, pk NoisePublicKey) (ss [NoisePublicKeySize]byte) {
|
||||
apk := (*[NoisePublicKeySize]byte)(&pk)
|
||||
ask := (*[NoisePrivateKeySize]byte)(sk)
|
||||
curve25519.ScalarMult(&ss, ask, apk)
|
||||
return ss
|
||||
}
|
||||
|
||||
func ConsumeHandshakeMsg(buf []byte, devicePubKey NoisePublicKey, devicePrivKey NoisePrivateKey) (string, error) {
|
||||
|
||||
var (
|
||||
hash [blake2s.Size]byte
|
||||
chainKey [blake2s.Size]byte
|
||||
)
|
||||
var err error
|
||||
var msg MessageInitiation
|
||||
reader := bytes.NewReader(buf[:])
|
||||
err = binary.Read(reader, binary.LittleEndian, &msg)
|
||||
if err != nil {
|
||||
log.Println("Failed to decode initiation message")
|
||||
return "", err
|
||||
}
|
||||
|
||||
if msg.Type != MessageInitiationType {
|
||||
return "", errors.New("not handshake initiate message")
|
||||
}
|
||||
log.Println("-----> HandSHAKE MESSAGE")
|
||||
mixHash(&hash, &InitialHash, devicePubKey[:])
|
||||
mixHash(&hash, &hash, msg.Ephemeral[:])
|
||||
mixKey(&chainKey, &InitialChainKey, msg.Ephemeral[:])
|
||||
|
||||
// decrypt static key
|
||||
var peerPK NoisePublicKey
|
||||
var key [chacha20poly1305.KeySize]byte
|
||||
ss := sharedSecret(&devicePrivKey, msg.Ephemeral)
|
||||
if isZero(ss[:]) {
|
||||
return "", errors.New("no secret")
|
||||
}
|
||||
KDF2(&chainKey, &key, chainKey[:], ss[:])
|
||||
aead, _ := chacha20poly1305.New(key[:])
|
||||
_, err = aead.Open(peerPK[:0], ZeroNonce[:], msg.Static[:], hash[:])
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
setZero(hash[:])
|
||||
setZero(chainKey[:])
|
||||
return base64.StdEncoding.EncodeToString(peerPK[:]), nil
|
||||
}
|
||||
|
||||
func loadExactHex(dst []byte, src string) error {
|
||||
slice, err := hex.DecodeString(src)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if len(slice) != len(dst) {
|
||||
return errors.New("hex string does not fit the slice")
|
||||
}
|
||||
copy(dst, slice)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (key NoisePrivateKey) IsZero() bool {
|
||||
var zero NoisePrivateKey
|
||||
return key.Equals(zero)
|
||||
}
|
||||
|
||||
func (key NoisePrivateKey) Equals(tar NoisePrivateKey) bool {
|
||||
return subtle.ConstantTimeCompare(key[:], tar[:]) == 1
|
||||
}
|
||||
|
||||
func (key *NoisePrivateKey) FromHex(src string) (err error) {
|
||||
err = loadExactHex(key[:], src)
|
||||
key.clamp()
|
||||
return
|
||||
}
|
||||
|
||||
func (key *NoisePrivateKey) FromMaybeZeroHex(src string) (err error) {
|
||||
err = loadExactHex(key[:], src)
|
||||
if key.IsZero() {
|
||||
return
|
||||
}
|
||||
key.clamp()
|
||||
return
|
||||
}
|
||||
func (sk *NoisePrivateKey) clamp() {
|
||||
sk[0] &= 248
|
||||
sk[31] = (sk[31] & 127) | 64
|
||||
}
|
||||
|
||||
func (key *NoisePublicKey) FromHex(src string) error {
|
||||
return loadExactHex(key[:], src)
|
||||
}
|
||||
|
||||
func (key NoisePublicKey) IsZero() bool {
|
||||
var zero NoisePublicKey
|
||||
return key.Equals(zero)
|
||||
}
|
||||
|
||||
func (key NoisePublicKey) Equals(tar NoisePublicKey) bool {
|
||||
return subtle.ConstantTimeCompare(key[:], tar[:]) == 1
|
||||
}
|
||||
|
||||
func (key *NoisePresharedKey) FromHex(src string) error {
|
||||
return loadExactHex(key[:], src)
|
||||
}
|
||||
|
||||
func GetDeviceKeys(ifaceName string) (NoisePrivateKey, NoisePublicKey, error) {
|
||||
wgPrivKey := wg.GetWgIfacePrivKey(ifaceName)
|
||||
wgPubKey := wg.GetWgIfacePubKey(ifaceName)
|
||||
|
||||
return wgPrivKey, wgPubKey, nil
|
||||
}
|
||||
|
|
@ -41,8 +41,8 @@ func AddNewPeer(wgInterface *wg.WGIface, peer *wgtypes.PeerConfig, peerAddr stri
|
|||
LocalKey: wgInterface.Device.PublicKey.String(),
|
||||
RemoteKey: peer.PublicKey.String(),
|
||||
WgInterface: wgInterface,
|
||||
|
||||
PeerConf: peer,
|
||||
IsExtClient: isExtClient,
|
||||
PeerConf: peer,
|
||||
}
|
||||
p := proxy.NewProxy(c)
|
||||
peerPort := common.NmProxyPort
|
||||
|
|
@ -65,15 +65,15 @@ func AddNewPeer(wgInterface *wg.WGIface, peer *wgtypes.PeerConfig, peerAddr stri
|
|||
}
|
||||
log.Printf("----> Established Remote Conn with RPeer: %s, ----> RAddr: %s", peer.PublicKey, remoteConn.String())
|
||||
|
||||
if !(isExtClient && isAttachedExtClient) {
|
||||
log.Printf("Starting proxy for Peer: %s\n", peer.PublicKey.String())
|
||||
err = p.Start(remoteConn)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
} else {
|
||||
log.Println("Not Starting Proxy for Attached ExtClient...")
|
||||
// if !(isExtClient && isAttachedExtClient) {
|
||||
log.Printf("Starting proxy for Peer: %s\n", peer.PublicKey.String())
|
||||
err = p.Start(remoteConn)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
// } else {
|
||||
// log.Println("Not Starting Proxy for Attached ExtClient...")
|
||||
// }
|
||||
|
||||
connConf := common.ConnConfig{
|
||||
Key: peer.PublicKey.String(),
|
||||
|
|
|
|||
|
|
@ -4,13 +4,8 @@ import (
|
|||
"context"
|
||||
"errors"
|
||||
"fmt"
|
||||
"log"
|
||||
"net"
|
||||
"time"
|
||||
|
||||
"github.com/google/gopacket"
|
||||
"github.com/google/gopacket/layers"
|
||||
"github.com/google/gopacket/pcap"
|
||||
"github.com/gravitl/netmaker/nm-proxy/common"
|
||||
"github.com/gravitl/netmaker/nm-proxy/wg"
|
||||
"golang.zx2c4.com/wireguard/wgctrl/wgtypes"
|
||||
|
|
@ -28,14 +23,14 @@ type Config struct {
|
|||
RemoteKey string
|
||||
LocalKey string
|
||||
WgInterface *wg.WGIface
|
||||
IsExtClient bool
|
||||
PeerConf *wgtypes.PeerConfig
|
||||
}
|
||||
|
||||
// Proxy - WireguardProxy proxies
|
||||
type Proxy struct {
|
||||
Ctx context.Context
|
||||
Cancel context.CancelFunc
|
||||
|
||||
Ctx context.Context
|
||||
Cancel context.CancelFunc
|
||||
Config Config
|
||||
RemoteConn *net.UDPAddr
|
||||
LocalConn net.Conn
|
||||
|
|
@ -107,136 +102,136 @@ func getBoardCastAddress() ([]net.Addr, error) {
|
|||
return nil, errors.New("couldn't obtain the broadcast addr")
|
||||
}
|
||||
|
||||
func StartSniffer(ctx context.Context, ifaceName, ingGwAddr, extClientAddr string, port int) {
|
||||
log.Println("Starting Packet Sniffer for iface: ", ifaceName)
|
||||
var (
|
||||
snapshotLen int32 = 1024
|
||||
promiscuous bool = false
|
||||
err error
|
||||
timeout time.Duration = 1 * time.Microsecond
|
||||
handle *pcap.Handle
|
||||
)
|
||||
// Open device
|
||||
handle, err = pcap.OpenLive(ifaceName, snapshotLen, promiscuous, timeout)
|
||||
if err != nil {
|
||||
log.Println("failed to start sniffer for iface: ", ifaceName, err)
|
||||
return
|
||||
}
|
||||
// if err := handle.SetBPFFilter(fmt.Sprintf("src %s and port %d", extClientAddr, port)); err != nil {
|
||||
// log.Println("failed to set bpf filter: ", err)
|
||||
// return
|
||||
// }
|
||||
defer handle.Close()
|
||||
// func StartSniffer(ctx context.Context, ifaceName, ingGwAddr, extClientAddr string, port int) {
|
||||
// log.Println("Starting Packet Sniffer for iface: ", ifaceName)
|
||||
// var (
|
||||
// snapshotLen int32 = 1024
|
||||
// promiscuous bool = false
|
||||
// err error
|
||||
// timeout time.Duration = 1 * time.Microsecond
|
||||
// handle *pcap.Handle
|
||||
// )
|
||||
// // Open device
|
||||
// handle, err = pcap.OpenLive(ifaceName, snapshotLen, promiscuous, timeout)
|
||||
// if err != nil {
|
||||
// log.Println("failed to start sniffer for iface: ", ifaceName, err)
|
||||
// return
|
||||
// }
|
||||
// // if err := handle.SetBPFFilter(fmt.Sprintf("src %s and port %d", extClientAddr, port)); err != nil {
|
||||
// // log.Println("failed to set bpf filter: ", err)
|
||||
// // return
|
||||
// // }
|
||||
// defer handle.Close()
|
||||
|
||||
// var tcp layers.TCP
|
||||
// var icmp layers.ICMPv4
|
||||
// var udp layers.UDP
|
||||
// parser := gopacket.NewDecodingLayerParser(layers.LayerTypeIPv4, &udp, &tcp, &icmp)
|
||||
// // var tcp layers.TCP
|
||||
// // var icmp layers.ICMPv4
|
||||
// // var udp layers.UDP
|
||||
// // parser := gopacket.NewDecodingLayerParser(layers.LayerTypeIPv4, &udp, &tcp, &icmp)
|
||||
|
||||
packetSource := gopacket.NewPacketSource(handle, handle.LinkType())
|
||||
for {
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
log.Println("Stopping packet sniffer for iface: ", ifaceName, " port: ", port)
|
||||
return
|
||||
default:
|
||||
packet, err := packetSource.NextPacket()
|
||||
if err == nil {
|
||||
//processPkt(ifaceName, packet)
|
||||
ipLayer := packet.Layer(layers.LayerTypeIPv4)
|
||||
if ipLayer != nil {
|
||||
fmt.Println("IPv4 layer detected.")
|
||||
ip, _ := ipLayer.(*layers.IPv4)
|
||||
// packetSource := gopacket.NewPacketSource(handle, handle.LinkType())
|
||||
// for {
|
||||
// select {
|
||||
// case <-ctx.Done():
|
||||
// log.Println("Stopping packet sniffer for iface: ", ifaceName, " port: ", port)
|
||||
// return
|
||||
// default:
|
||||
// packet, err := packetSource.NextPacket()
|
||||
// if err == nil {
|
||||
// //processPkt(ifaceName, packet)
|
||||
// ipLayer := packet.Layer(layers.LayerTypeIPv4)
|
||||
// if ipLayer != nil {
|
||||
// fmt.Println("IPv4 layer detected.")
|
||||
// ip, _ := ipLayer.(*layers.IPv4)
|
||||
|
||||
// IP layer variables:
|
||||
// Version (Either 4 or 6)
|
||||
// IHL (IP Header Length in 32-bit words)
|
||||
// TOS, Length, Id, Flags, FragOffset, TTL, Protocol (TCP?),
|
||||
// Checksum, SrcIP, DstIP
|
||||
fmt.Println("#########################")
|
||||
fmt.Printf("From %s to %s\n", ip.SrcIP, ip.DstIP)
|
||||
fmt.Println("Protocol: ", ip.Protocol.String())
|
||||
if (ip.SrcIP.String() == extClientAddr && ip.DstIP.String() != ingGwAddr) ||
|
||||
(ip.DstIP.String() == extClientAddr && ip.SrcIP.String() != ingGwAddr) {
|
||||
// // IP layer variables:
|
||||
// // Version (Either 4 or 6)
|
||||
// // IHL (IP Header Length in 32-bit words)
|
||||
// // TOS, Length, Id, Flags, FragOffset, TTL, Protocol (TCP?),
|
||||
// // Checksum, SrcIP, DstIP
|
||||
// fmt.Println("#########################")
|
||||
// fmt.Printf("From %s to %s\n", ip.SrcIP, ip.DstIP)
|
||||
// fmt.Println("Protocol: ", ip.Protocol.String())
|
||||
// if (ip.SrcIP.String() == extClientAddr && ip.DstIP.String() != ingGwAddr) ||
|
||||
// (ip.DstIP.String() == extClientAddr && ip.SrcIP.String() != ingGwAddr) {
|
||||
|
||||
log.Println("-----> Fowarding PKT From: ", ip.SrcIP, " to: ", ip.DstIP)
|
||||
c, err := net.Dial("ip", ip.DstIP.String())
|
||||
if err == nil {
|
||||
c.Write(ip.Payload)
|
||||
c.Close()
|
||||
} else {
|
||||
log.Println("------> Failed to forward packet from sniffer: ", err)
|
||||
// log.Println("-----> Fowarding PKT From: ", ip.SrcIP, " to: ", ip.DstIP)
|
||||
// c, err := net.Dial("ip", ip.DstIP.String())
|
||||
// if err == nil {
|
||||
// c.Write(ip.Payload)
|
||||
// c.Close()
|
||||
// } else {
|
||||
// log.Println("------> Failed to forward packet from sniffer: ", err)
|
||||
|
||||
}
|
||||
}
|
||||
// }
|
||||
// }
|
||||
|
||||
fmt.Println("#########################")
|
||||
}
|
||||
}
|
||||
}
|
||||
// fmt.Println("#########################")
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
}
|
||||
}
|
||||
// }
|
||||
// }
|
||||
|
||||
func processPkt(iface string, packet gopacket.Packet) {
|
||||
// Let's see if the packet is an ethernet packet
|
||||
// ethernetLayer := packet.Layer(layers.LayerTypeEthernet)
|
||||
// if ethernetLayer != nil {
|
||||
// fmt.Println("Ethernet layer detected.")
|
||||
// ethernetPacket, _ := ethernetLayer.(*layers.Ethernet)
|
||||
// fmt.Println("Source MAC: ", ethernetPacket.SrcMAC)
|
||||
// fmt.Println("Destination MAC: ", ethernetPacket.DstMAC)
|
||||
// // Ethernet type is typically IPv4 but could be ARP or other
|
||||
// fmt.Println("Ethernet type: ", ethernetPacket.EthernetType)
|
||||
// fmt.Println()
|
||||
// }
|
||||
// func processPkt(iface string, packet gopacket.Packet) {
|
||||
// // Let's see if the packet is an ethernet packet
|
||||
// // ethernetLayer := packet.Layer(layers.LayerTypeEthernet)
|
||||
// // if ethernetLayer != nil {
|
||||
// // fmt.Println("Ethernet layer detected.")
|
||||
// // ethernetPacket, _ := ethernetLayer.(*layers.Ethernet)
|
||||
// // fmt.Println("Source MAC: ", ethernetPacket.SrcMAC)
|
||||
// // fmt.Println("Destination MAC: ", ethernetPacket.DstMAC)
|
||||
// // // Ethernet type is typically IPv4 but could be ARP or other
|
||||
// // fmt.Println("Ethernet type: ", ethernetPacket.EthernetType)
|
||||
// // fmt.Println()
|
||||
// // }
|
||||
|
||||
// Let's see if the packet is IP (even though the ether type told us)
|
||||
ipLayer := packet.Layer(layers.LayerTypeIPv4)
|
||||
if ipLayer != nil {
|
||||
fmt.Println("IPv4 layer detected.")
|
||||
ip, _ := ipLayer.(*layers.IPv4)
|
||||
// // Let's see if the packet is IP (even though the ether type told us)
|
||||
// ipLayer := packet.Layer(layers.LayerTypeIPv4)
|
||||
// if ipLayer != nil {
|
||||
// fmt.Println("IPv4 layer detected.")
|
||||
// ip, _ := ipLayer.(*layers.IPv4)
|
||||
|
||||
// IP layer variables:
|
||||
// Version (Either 4 or 6)
|
||||
// IHL (IP Header Length in 32-bit words)
|
||||
// TOS, Length, Id, Flags, FragOffset, TTL, Protocol (TCP?),
|
||||
// Checksum, SrcIP, DstIP
|
||||
fmt.Printf("From %s to %s\n", ip.SrcIP, ip.DstIP)
|
||||
fmt.Println("Protocol: ", ip.Protocol)
|
||||
fmt.Println()
|
||||
// // IP layer variables:
|
||||
// // Version (Either 4 or 6)
|
||||
// // IHL (IP Header Length in 32-bit words)
|
||||
// // TOS, Length, Id, Flags, FragOffset, TTL, Protocol (TCP?),
|
||||
// // Checksum, SrcIP, DstIP
|
||||
// fmt.Printf("From %s to %s\n", ip.SrcIP, ip.DstIP)
|
||||
// fmt.Println("Protocol: ", ip.Protocol)
|
||||
// fmt.Println()
|
||||
|
||||
}
|
||||
// }
|
||||
|
||||
// udpLayer := packet.Layer(layers.LayerTypeUDP)
|
||||
// if udpLayer != nil {
|
||||
// udp, _ := udpLayer.(*layers.UDP)
|
||||
// fmt.Printf("UDP: From port %d to %d\n", udp.SrcPort, udp.DstPort)
|
||||
// fmt.Println()
|
||||
// }
|
||||
// // udpLayer := packet.Layer(layers.LayerTypeUDP)
|
||||
// // if udpLayer != nil {
|
||||
// // udp, _ := udpLayer.(*layers.UDP)
|
||||
// // fmt.Printf("UDP: From port %d to %d\n", udp.SrcPort, udp.DstPort)
|
||||
// // fmt.Println()
|
||||
// // }
|
||||
|
||||
// // Iterate over all layers, printing out each layer type
|
||||
// fmt.Println("All packet layers:")
|
||||
// for _, layer := range packet.Layers() {
|
||||
// fmt.Println("- ", layer.LayerType())
|
||||
// }
|
||||
// // // Iterate over all layers, printing out each layer type
|
||||
// // fmt.Println("All packet layers:")
|
||||
// // for _, layer := range packet.Layers() {
|
||||
// // fmt.Println("- ", layer.LayerType())
|
||||
// // }
|
||||
|
||||
// When iterating through packet.Layers() above,
|
||||
// if it lists Payload layer then that is the same as
|
||||
// this applicationLayer. applicationLayer contains the payload
|
||||
// applicationLayer := packet.ApplicationLayer()
|
||||
// if applicationLayer != nil {
|
||||
// fmt.Println("Application layer/Payload found.")
|
||||
// fmt.Printf("%s\n", applicationLayer.Payload())
|
||||
// // When iterating through packet.Layers() above,
|
||||
// // if it lists Payload layer then that is the same as
|
||||
// // this applicationLayer. applicationLayer contains the payload
|
||||
// // applicationLayer := packet.ApplicationLayer()
|
||||
// // if applicationLayer != nil {
|
||||
// // fmt.Println("Application layer/Payload found.")
|
||||
// // fmt.Printf("%s\n", applicationLayer.Payload())
|
||||
|
||||
// // Search for a string inside the payload
|
||||
// if strings.Contains(string(applicationLayer.Payload()), "HTTP") {
|
||||
// fmt.Println("HTTP found!")
|
||||
// }
|
||||
// }
|
||||
// // // Search for a string inside the payload
|
||||
// // if strings.Contains(string(applicationLayer.Payload()), "HTTP") {
|
||||
// // fmt.Println("HTTP found!")
|
||||
// // }
|
||||
// // }
|
||||
|
||||
// Check for errors
|
||||
if err := packet.ErrorLayer(); err != nil {
|
||||
fmt.Println("Error decoding some part of the packet:", err)
|
||||
}
|
||||
}
|
||||
// // Check for errors
|
||||
// if err := packet.ErrorLayer(); err != nil {
|
||||
// fmt.Println("Error decoding some part of the packet:", err)
|
||||
// }
|
||||
// }
|
||||
|
|
|
|||
|
|
@ -59,14 +59,18 @@ func (p *Proxy) ProxyToRemote() {
|
|||
log.Println("ERRR READ: ", err)
|
||||
continue
|
||||
}
|
||||
|
||||
//go func(buf []byte, n int) {
|
||||
ifaceConf := common.WgIFaceMap[p.Config.WgInterface.Name]
|
||||
if peerI, ok := ifaceConf.PeerMap[p.Config.RemoteKey]; ok {
|
||||
var srcPeerKeyHash, dstPeerKeyHash string
|
||||
buf, n, srcPeerKeyHash, dstPeerKeyHash = packet.ProcessPacketBeforeSending(buf, n, peerI.Config.LocalKey, peerI.Config.Key)
|
||||
if err != nil {
|
||||
log.Println("failed to process pkt before sending: ", err)
|
||||
if !p.Config.IsExtClient {
|
||||
buf, n, srcPeerKeyHash, dstPeerKeyHash = packet.ProcessPacketBeforeSending(buf, n, peerI.Config.LocalKey, peerI.Config.Key)
|
||||
if err != nil {
|
||||
log.Println("failed to process pkt before sending: ", err)
|
||||
}
|
||||
}
|
||||
|
||||
log.Printf("PROXING TO REMOTE!!!---> %s >>>>> %s >>>>> %s [[ SrcPeerHash: %s, DstPeerHash: %s ]]\n",
|
||||
p.LocalConn.LocalAddr(), server.NmProxyServer.Server.LocalAddr().String(), p.RemoteConn.String(), srcPeerKeyHash, dstPeerKeyHash)
|
||||
} else {
|
||||
|
|
|
|||
|
|
@ -60,11 +60,13 @@ func (p *ProxyServer) Listen(ctx context.Context) {
|
|||
log.Println("RECV ERROR: ", err)
|
||||
continue
|
||||
}
|
||||
orgN := n
|
||||
//go func(buffer []byte, source *net.UDPAddr, n int) {
|
||||
|
||||
var srcPeerKeyHash, dstPeerKeyHash string
|
||||
n, srcPeerKeyHash, dstPeerKeyHash = packet.ExtractInfo(buffer, n)
|
||||
//log.Printf("--------> RECV PKT , [SRCKEYHASH: %s], SourceIP: [%s] \n", srcPeerKeyHash, source.IP.String())
|
||||
log.Printf("--------> RECV PKT , [SRCKEYHASH: %s], SourceIP: [%s] \n", srcPeerKeyHash, source.IP.String())
|
||||
|
||||
if _, ok := common.WgIfaceKeyMap[dstPeerKeyHash]; !ok {
|
||||
// if common.IsIngressGateway {
|
||||
// log.Println("----> fowarding PKT to EXT client...")
|
||||
|
|
@ -125,25 +127,45 @@ func (p *ProxyServer) Listen(ctx context.Context) {
|
|||
log.Println("Failed to proxy to Wg local interface: ", err)
|
||||
//continue
|
||||
}
|
||||
continue
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
// // forward to all interfaces
|
||||
// for _, ifaceCfg := range common.WgIfaceKeyMap {
|
||||
// log.Println("###--------> Forwarding Unknown PKT to ", ifaceCfg.Interface)
|
||||
// conn, err := net.DialUDP("udp", nil, ifaceCfg.Endpoint)
|
||||
// if err == nil {
|
||||
// _, err := conn.Write(buffer[:n])
|
||||
// if err != nil {
|
||||
// log.Println("Failed to forward the unknown pkt to ifcace: ", ifaceCfg.Interface, err)
|
||||
// }
|
||||
// conn.Close()
|
||||
// }
|
||||
if peerInfo, ok := common.ExtSourceIpMap[source.String()]; ok {
|
||||
if ifaceConf, ok := common.WgIFaceMap[peerInfo.Interface]; ok {
|
||||
if peerI, ok := ifaceConf.PeerMap[peerInfo.PeerKey]; ok {
|
||||
log.Printf("PROXING TO LOCAL!!!---> %s <<<< %s <<<<<<<< %s [[ RECV PKT [SRCKEYHASH: %s], [DSTKEYHASH: %s], SourceIP: [%s] ]]\n",
|
||||
peerI.Proxy.LocalConn.RemoteAddr(), peerI.Proxy.LocalConn.LocalAddr(),
|
||||
fmt.Sprintf("%s:%d", source.IP.String(), source.Port), srcPeerKeyHash, dstPeerKeyHash, source.IP.String())
|
||||
_, err = peerI.Proxy.LocalConn.Write(buffer[:orgN])
|
||||
if err != nil {
|
||||
log.Println("Failed to proxy to Wg local interface: ", err)
|
||||
//continue
|
||||
}
|
||||
continue
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
// consume handshake message for ext clients
|
||||
devPriv, devPubkey, err := packet.GetDeviceKeys(common.InterfaceName)
|
||||
if err == nil {
|
||||
peerPubKey, err := packet.ConsumeHandshakeMsg(buffer[:orgN], devPubkey, devPriv)
|
||||
if err != nil {
|
||||
log.Println("---------> @@@ failed to decode HS: ", err)
|
||||
} else {
|
||||
log.Println("--------> Got HandShake from peer: ", peerPubKey, source)
|
||||
if val, ok := common.ExtClientsWaitTh[peerPubKey]; ok {
|
||||
val.CommChan <- source
|
||||
}
|
||||
}
|
||||
|
||||
} else {
|
||||
log.Println("failed to get device keys: ", err)
|
||||
}
|
||||
|
||||
// }
|
||||
//}(buffer, source, n)
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -80,18 +80,33 @@ func (w *WGIface) GetWgIface(iface string) error {
|
|||
return nil
|
||||
}
|
||||
|
||||
func GetWgIfacePubKey(iface string) string {
|
||||
func GetWgIfacePubKey(iface string) [32]byte {
|
||||
wgClient, err := wgctrl.New()
|
||||
if err != nil {
|
||||
log.Println("Error fetching pub key: ", iface, err)
|
||||
return ""
|
||||
return [32]byte{}
|
||||
}
|
||||
dev, err := wgClient.Device(iface)
|
||||
if err != nil {
|
||||
log.Println("Error fetching pub key: ", iface, err)
|
||||
return ""
|
||||
return [32]byte{}
|
||||
}
|
||||
return dev.PublicKey.String()
|
||||
|
||||
return dev.PublicKey
|
||||
}
|
||||
|
||||
func GetWgIfacePrivKey(iface string) [32]byte {
|
||||
wgClient, err := wgctrl.New()
|
||||
if err != nil {
|
||||
log.Println("Error fetching pub key: ", iface, err)
|
||||
return [32]byte{}
|
||||
}
|
||||
dev, err := wgClient.Device(iface)
|
||||
if err != nil {
|
||||
log.Println("Error fetching pub key: ", iface, err)
|
||||
return [32]byte{}
|
||||
}
|
||||
return dev.PrivateKey
|
||||
}
|
||||
|
||||
// parseAddress parse a string ("1.2.3.4/24") address to WG Address
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue