WIP: Update struct decode and encode #2
@ -6,8 +6,8 @@ import (
|
||||
"io"
|
||||
"log"
|
||||
"net"
|
||||
"net/netip"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"sirherobrine23.com.br/Minecraft-Server/go-pproxit/internal/pipe"
|
||||
)
|
||||
@ -25,6 +25,7 @@ type client struct {
|
||||
fromAgent, toClient net.Conn
|
||||
bufferCache *bytes.Buffer
|
||||
bufioCache *bufio.Reader
|
||||
LastPing time.Time
|
||||
}
|
||||
|
||||
type UDPServer struct {
|
||||
@ -37,6 +38,29 @@ type UDPServer struct {
|
||||
rw sync.RWMutex
|
||||
}
|
||||
|
||||
func ListenUDP(network string, laddr *net.UDPAddr) (*UDPServer, error) {
|
||||
conn, err := net.ListenUDP(network, laddr)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var root = &UDPServer{
|
||||
rootUdp: conn,
|
||||
peers: make(map[string]*client),
|
||||
newPeer: make(chan net.Conn),
|
||||
peerError: make(chan error),
|
||||
}
|
||||
go root.handler()
|
||||
return root, nil
|
||||
}
|
||||
|
||||
func Listen(Network, address string) (net.Listener, error) {
|
||||
ip, err := net.ResolveUDPAddr(Network, address)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return ListenUDP(Network, ip)
|
||||
}
|
||||
|
||||
// Local address
|
||||
func (udpListen *UDPServer) Addr() net.Addr {
|
||||
return udpListen.rootUdp.LocalAddr()
|
||||
@ -69,17 +93,23 @@ func (udpListen *UDPServer) Accept() (peer net.Conn, err error) {
|
||||
}
|
||||
|
||||
func (udpListen *UDPServer) handler() {
|
||||
buff := make([]byte, 32*1024)
|
||||
for {
|
||||
buff := make([]byte, 1480)
|
||||
n, from, err := udpListen.rootUdp.ReadFromUDP(buff)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
udpListen.rw.Lock()
|
||||
if nt, exist := udpListen.peers[from.String()]; exist {
|
||||
if (time.Now().UnixMicro() - nt.LastPing.UnixMicro()) > 100_000_000 {
|
||||
delete(udpListen.peers, from.String())
|
||||
}
|
||||
}
|
||||
|
||||
if _, exist := udpListen.peers[from.String()]; !exist {
|
||||
c := new(client)
|
||||
|
||||
c.LastPing = time.Now()
|
||||
c.bufferCache = new(bytes.Buffer)
|
||||
c.bufioCache = bufio.NewReader(c.bufferCache)
|
||||
|
||||
@ -107,30 +137,3 @@ func (udpListen *UDPServer) handler() {
|
||||
udpListen.rw.RUnlock()
|
||||
}
|
||||
}
|
||||
|
||||
func listenRoot(network string, laddr *net.UDPAddr) (net.Listener, error) {
|
||||
conn, err := net.ListenUDP(network, laddr)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var root = &UDPServer{
|
||||
rootUdp: conn,
|
||||
peers: make(map[string]*client),
|
||||
newPeer: make(chan net.Conn),
|
||||
peerError: make(chan error),
|
||||
}
|
||||
go root.handler()
|
||||
return root, nil
|
||||
}
|
||||
|
||||
func ListenAddrPort(Network string, address netip.AddrPort) (net.Listener, error) {
|
||||
return listenRoot(Network, net.UDPAddrFromAddrPort(address))
|
||||
}
|
||||
|
||||
func Listen(Network, address string) (net.Listener, error) {
|
||||
ip, err := net.ResolveUDPAddr(Network, address)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return listenRoot(Network, ip)
|
||||
}
|
||||
|
124
tun.go
124
tun.go
@ -1,12 +1,16 @@
|
||||
package gopproxit
|
||||
|
||||
import (
|
||||
"io"
|
||||
"maps"
|
||||
"net"
|
||||
"net/netip"
|
||||
"reflect"
|
||||
"slices"
|
||||
"sync"
|
||||
|
||||
"sirherobrine23.com.br/Minecraft-Server/go-pproxit/internal/structcode"
|
||||
"sirherobrine23.com.br/Minecraft-Server/go-pproxit/internal/udplisterner"
|
||||
"sirherobrine23.com.br/Minecraft-Server/go-pproxit/proto"
|
||||
)
|
||||
|
||||
@ -17,9 +21,11 @@ type Tunnel struct {
|
||||
Done chan struct{} // Closed connection
|
||||
|
||||
TCPServer *net.TCPListener
|
||||
UDPServer *net.UDPConn
|
||||
TCPConns map[string]net.Conn
|
||||
UDPConns map[string]net.Conn
|
||||
UDPServer *udplisterner.UDPServer
|
||||
|
||||
TCPLocker, UDPLocker sync.Locker
|
||||
TCPConns map[string]net.Conn
|
||||
UDPConns map[string]net.Conn
|
||||
}
|
||||
|
||||
func NewTun(conn net.Conn, Agent *proto.AgentInfo) *Tunnel {
|
||||
@ -28,6 +34,7 @@ func NewTun(conn net.Conn, Agent *proto.AgentInfo) *Tunnel {
|
||||
tun.Controller = conn
|
||||
|
||||
// Listen clients
|
||||
tun.TCPLocker, tun.UDPLocker = &sync.Mutex{}, &sync.Mutex{}
|
||||
tun.TCPConns, tun.UDPConns = make(map[string]net.Conn), make(map[string]net.Conn)
|
||||
tun.TunErr = make(chan error)
|
||||
tun.Done = make(chan struct{})
|
||||
@ -50,6 +57,14 @@ func (tun *Tunnel) Close() error {
|
||||
if tun.Controller != nil {
|
||||
tun.Controller.Close()
|
||||
}
|
||||
if tun.TCPServer != nil {
|
||||
tun.TCPServer.Close()
|
||||
tun.TCPServer = nil
|
||||
}
|
||||
if tun.UDPServer != nil {
|
||||
tun.UDPServer.Close()
|
||||
tun.UDPServer = nil
|
||||
}
|
||||
|
||||
for _, d := range slices.Collect(maps.Values(tun.TCPConns)) {
|
||||
d.Close()
|
||||
@ -73,7 +88,72 @@ func (tun *Tunnel) sendErr(err error) {
|
||||
tun.TunErr <- err
|
||||
}
|
||||
|
||||
func (tun *Tunnel) Handler() {}
|
||||
func (tun *Tunnel) Handler() {
|
||||
defer tun.Close()
|
||||
for {
|
||||
var req proto.Request
|
||||
if err := structcode.NewDecode(tun.Controller, &req); err != nil {
|
||||
if err == io.EOF {
|
||||
return
|
||||
}
|
||||
continue
|
||||
}
|
||||
|
||||
go func(req proto.Request) {
|
||||
if data := *req.ClientClose; req.ClientClose != nil {
|
||||
switch data.Proto {
|
||||
case proto.ProtoTCP:
|
||||
if client, ok := tun.TCPConns[data.Client.String()]; ok {
|
||||
client.Close()
|
||||
delete(tun.TCPConns, data.Client.String())
|
||||
}
|
||||
case proto.ProtoUDP:
|
||||
if client, ok := tun.UDPConns[data.Client.String()]; ok {
|
||||
client.Close()
|
||||
delete(tun.UDPConns, data.Client.String())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if data := *req.DataTX; req.DataTX != nil {
|
||||
var conn net.Conn
|
||||
var ok bool
|
||||
switch data.Client.Proto {
|
||||
case proto.ProtoTCP:
|
||||
if conn, ok = tun.TCPConns[data.Client.Client.String()]; !ok {
|
||||
return
|
||||
}
|
||||
case proto.ProtoUDP:
|
||||
if conn, ok = tun.UDPConns[data.Client.Client.String()]; !ok {
|
||||
return
|
||||
}
|
||||
}
|
||||
conn.Write(data.Data)
|
||||
}
|
||||
}(req)
|
||||
}
|
||||
}
|
||||
|
||||
type rx struct {
|
||||
root net.Conn
|
||||
proto proto.Protoc
|
||||
}
|
||||
|
||||
func (t rx) Write(p []byte) (int, error) {
|
||||
err := structcode.NewEncode(t.root, proto.Response{
|
||||
DataRX: &proto.ClientData{
|
||||
Data: p,
|
||||
Client: proto.Client{
|
||||
Proto: t.proto,
|
||||
Client: netip.MustParseAddrPort(t.root.RemoteAddr().String()),
|
||||
},
|
||||
},
|
||||
})
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
return len(p), nil
|
||||
}
|
||||
|
||||
func (tun *Tunnel) TCPServerhandler() {
|
||||
var err error
|
||||
@ -81,6 +161,40 @@ func (tun *Tunnel) TCPServerhandler() {
|
||||
tun.sendErr(err)
|
||||
return
|
||||
}
|
||||
defer tun.TCPServer.Close()
|
||||
for {
|
||||
conn, err := tun.TCPServer.Accept()
|
||||
if err != nil {
|
||||
tun.sendErr(err)
|
||||
return
|
||||
}
|
||||
go func() {
|
||||
tun.TCPLocker.Lock()
|
||||
tun.TCPConns[conn.RemoteAddr().String()] = conn
|
||||
tun.TCPLocker.Unlock()
|
||||
io.Copy(&rx{root: conn, proto: proto.ProtoTCP}, conn)
|
||||
}()
|
||||
}
|
||||
}
|
||||
|
||||
func (tun *Tunnel) UDPServerhandler() {}
|
||||
func (tun *Tunnel) UDPServerhandler() {
|
||||
var err error
|
||||
if tun.UDPServer, err = udplisterner.ListenUDP("udp", net.UDPAddrFromAddrPort(netip.AddrPortFrom(netip.IPv4Unspecified(), tun.Agent.TCPPort))); err != nil {
|
||||
tun.sendErr(err)
|
||||
return
|
||||
}
|
||||
defer tun.UDPServer.Close()
|
||||
for {
|
||||
conn, err := tun.UDPServer.Accept()
|
||||
if err != nil {
|
||||
tun.sendErr(err)
|
||||
return
|
||||
}
|
||||
go func() {
|
||||
tun.UDPLocker.Lock()
|
||||
tun.UDPConns[conn.RemoteAddr().String()] = conn
|
||||
tun.UDPLocker.Unlock()
|
||||
io.Copy(&rx{root: conn, proto: proto.ProtoUDP}, conn)
|
||||
}()
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user