Files
NetHive/core/engine/routine.go
2024-04-26 18:11:56 +08:00

90 lines
1.8 KiB
Go

package engine
import (
"fmt"
"github.com/wlynxg/NetHive/core/protocol"
)
// RoutineTUNReader loop to read packets from TUN
func (e *Engine) RoutineTUNReader() {
var (
buff = make([]byte, BuffSize)
err error
n int
)
for {
n, err = e.device.Read(buff)
if err != nil {
e.errChan <- fmt.Errorf("[RoutineTUNReader]: %s", err)
return
}
ip, err := protocol.ParseIP(buff[:n])
if err != nil {
e.log.Warnf("[RoutineTUNReader] drop packet, because %s", err)
continue
}
payload := Payload{
Src: ip.Src(),
Dst: ip.Dst(),
Data: make([]byte, n),
}
copy(payload.Data, buff[:n])
select {
case e.devReader <- payload:
default:
e.log.Warnf("[RoutineTUNReader] drop packet: %s, because the sending queue is already full", payload.Dst)
}
}
}
// RoutineTUNWriter loop writing packets to TUN
func (e *Engine) RoutineTUNWriter() {
var (
payload Payload
err error
)
for payload = range e.devWriter {
_, err = e.device.Write(payload.Data)
if err != nil {
e.log.Error(e.ctx, fmt.Errorf("[RoutineTUNWriter]: %s", err))
return
}
}
}
// RoutineRouteTableWriter loop sending the data packet to the corresponding channel according to the routing table
func (e *Engine) RoutineRouteTableWriter() {
var (
payload Payload
)
for payload = range e.devReader {
var conn PacketChan
e.log.Debugf("%s -> %s", payload.Src, payload.Dst)
c, ok := e.routeTable.addr.Load(payload.Dst)
if ok {
conn = c
} else {
c, err := e.addConnByDst(payload.Dst)
if err != nil {
e.log.Warnf("[RoutineRouteTableWriter] drop packet: %s, because %s", payload.Dst, err)
continue
}
conn = c
}
if conn == nil {
continue
}
select {
case conn <- payload:
default:
e.log.Warnf("[RoutineRouteTableWriter] drop packet: %s, because the sending queue is already full", payload.Dst)
}
}
}