diff --git a/listener/tun/ipstack/gvisor/tun.go b/listener/tun/ipstack/gvisor/tun.go index 528bf16a..1445da47 100644 --- a/listener/tun/ipstack/gvisor/tun.go +++ b/listener/tun/ipstack/gvisor/tun.go @@ -54,6 +54,7 @@ func NewAdapter(device dev.TunDevice, conf config.Tun, tcpIn chan<- C.ConnContex NetworkProtocols: []stack.NetworkProtocolFactory{ipv4.NewProtocol, ipv6.NewProtocol}, TransportProtocols: []stack.TransportProtocolFactory{tcp.NewProtocol, udp.NewProtocol}, }) + adapter := &gvisorAdapter{ device: device, ipstack: ipstack, @@ -95,7 +96,8 @@ func NewAdapter(device dev.TunDevice, conf config.Tun, tcpIn chan<- C.ConnContex r.Complete(true) return } - r.Complete(false) + + defer r.Complete(false) conn := gonet.NewTCPConn(&wq, ep) @@ -110,6 +112,7 @@ func NewAdapter(device dev.TunDevice, conf config.Tun, tcpIn chan<- C.ConnContex target := getAddr(ep.Info().(*stack.TransportEndpointInfo).ID) tcpIn <- inbound.NewSocket(target, conn, C.TUN) }) + ipstack.SetTransportProtocolHandler(tcp.ProtocolNumber, tcpFwd.HandlePacket) // UDP handler @@ -200,24 +203,31 @@ func (t *gvisorAdapter) AsLinkEndpoint() (result stack.LinkEndpoint, err error) log.Errorln("can not read from tun: %v", err) continue } + var p tcpip.NetworkProtocolNumber switch header.IPVersion(packet) { case header.IPv4Version: p = header.IPv4ProtocolNumber case header.IPv6Version: p = header.IPv6ProtocolNumber + default: + log.Warnln("invalid IP version:%d", header.IPVersion(packet)) + continue } + if linkEP.IsAttached() { - packetBuffer := stack.NewPacketBuffer(stack.PacketBufferOptions{ + pkt := stack.NewPacketBuffer(stack.PacketBufferOptions{ Data: buffer.View(packet[:n]).ToVectorisedView(), }) - linkEP.InjectInbound(p, packetBuffer) - packetBuffer.DecRef() + linkEP.InjectInbound(p, pkt) + // release memory + pkt.DecRef() } else { log.Debugln("received packet from tun when %s is not attached to any dispatcher.", t.device.Name()) } } + t.wg.Done() t.Close() log.Debugln("%v stop read loop", t.device.Name())