snapshot: sagernet/gvisor v0.0.0-20260727.0-sing-box-mod.1 + SPEC 048 guard
Обновление снапшота с v0.0.0-20250811.0 на пин, которого требует sing-box после мержа 235 коммитов (upstream d620bbbf2 "Update gvisor to 20260727.0"). Прежний снапшот был взят 2026-08-04 ровно с той версии, на которой тогда стоял апстрим; разрыв возник 2026-08-05 вместе с его бампом. За год апстрим-gvisor изменил ~14 000 строк в 292 файлах. Значимое для нас — сетевой стек: tcp/connect.go (PMTU-discovery + исправление начального RTT/RTO: раньше задержка ACK внутри стека завышала стартовый таймаут на несколько RTT), tcp/snd.go, tcp/rcv.go, stack/conntrack.go, stack/packet_buffer.go. Всего 30 файлов в TCP и 37 в stack. Баг SPEC 048 апстрим НЕ исправил — проверено по коду новой версии: handleConnecting по-прежнему проверяет состояние endpoint'а, но не ep.h, а performHandshake так же зануляет h и отпускает мьютекс до Close(). Поэтому guard перенесён (12 строк) вместе со своим тестом (45 строк). Red/green проверен на новой базе: без guard'а тест падает с той же nil-паникой, что в полевом крашдампе; с ним зелёный.
This commit is contained in:
parent
ffebe42860
commit
117243aa02
293 changed files with 16413 additions and 2842 deletions
|
|
@ -46,7 +46,6 @@ type processor struct {
|
|||
|
||||
func (p *processor) start(wg *sync.WaitGroup) {
|
||||
defer wg.Done()
|
||||
defer p.sleeper.Done()
|
||||
for {
|
||||
switch w := p.sleeper.Fetch(true); {
|
||||
case w == &p.packetWaker:
|
||||
|
|
@ -128,9 +127,10 @@ func (m *processorManager) start() {
|
|||
}
|
||||
|
||||
// afterLoad is invoked by stateify.
|
||||
func (m *processorManager) afterLoad(context.Context) {
|
||||
m.wg.Add(len(m.processors))
|
||||
m.start()
|
||||
func (m *processorManager) afterLoad(ctx context.Context) {
|
||||
// Close all the old/saved processors. There are new NICs and
|
||||
// processors created during restore.
|
||||
m.close()
|
||||
}
|
||||
|
||||
func (m *processorManager) connectionHash(cid *connectionID) uint32 {
|
||||
|
|
@ -215,34 +215,47 @@ func tcpipConnectionID(pkt *stack.PacketBuffer) (connectionID, bool) {
|
|||
return cid, true
|
||||
}
|
||||
ipHdr := header.IPv6(h)
|
||||
cid.srcAddr = ipHdr.SourceAddressSlice()
|
||||
cid.dstAddr = ipHdr.DestinationAddressSlice()
|
||||
cid.proto = header.IPv6ProtocolNumber
|
||||
|
||||
var tcpHdr header.TCP
|
||||
if tcpip.TransportProtocolNumber(ipHdr.NextHeader()) == header.TCPProtocolNumber {
|
||||
tcpHdr = header.TCP(h[header.IPv6FixedHeaderSize:][:tcpSrcDstPortLen])
|
||||
if !header.IsExtensionHeader(ipHdr.NextHeader()) {
|
||||
// Known transport protocols(not just TCP) store the src and dst ports
|
||||
// in the first 4 bytes after the IPv6 fixed header.
|
||||
tcpHdr := header.TCP(h[header.IPv6FixedHeaderSize:][:tcpSrcDstPortLen])
|
||||
cid.srcPort = tcpHdr.SourcePort()
|
||||
cid.dstPort = tcpHdr.DestinationPort()
|
||||
} else {
|
||||
// Slow path for IPv6 extension headers :(.
|
||||
dataBuf := pkt.Data().ToBuffer()
|
||||
dataBuf.TrimFront(header.IPv6MinimumSize)
|
||||
it := header.MakeIPv6PayloadIterator(header.IPv6ExtensionHeaderIdentifier(ipHdr.NextHeader()), dataBuf)
|
||||
defer it.Release()
|
||||
// All fragment packets need to be processed by the same goroutine, so
|
||||
// only record the ports if this is not a fragment packet.
|
||||
var isFragment bool
|
||||
for {
|
||||
hdr, done, err := it.Next()
|
||||
if done || err != nil {
|
||||
break
|
||||
}
|
||||
if fh, ok := hdr.(header.IPv6FragmentExtHdr); ok && !fh.IsAtomic() {
|
||||
isFragment = true
|
||||
}
|
||||
hdr.Release()
|
||||
}
|
||||
h, ok = pkt.Data().PullUp(int(it.HeaderOffset()) + tcpSrcDstPortLen)
|
||||
if !ok {
|
||||
return cid, true
|
||||
if !isFragment {
|
||||
h, ok = pkt.Data().PullUp(int(it.HeaderOffset()) + tcpSrcDstPortLen)
|
||||
if !ok {
|
||||
return cid, true
|
||||
}
|
||||
// Known transport protocols store the src and dst ports
|
||||
// in the first 4 bytes after the IPv6 fixed header.
|
||||
tcpHdr := header.TCP(h[it.HeaderOffset():][:tcpSrcDstPortLen])
|
||||
cid.srcPort = tcpHdr.SourcePort()
|
||||
cid.dstPort = tcpHdr.DestinationPort()
|
||||
}
|
||||
tcpHdr = header.TCP(h[it.HeaderOffset():][:tcpSrcDstPortLen])
|
||||
}
|
||||
cid.srcAddr = ipHdr.SourceAddressSlice()
|
||||
cid.dstAddr = ipHdr.DestinationAddressSlice()
|
||||
cid.srcPort = tcpHdr.SourcePort()
|
||||
cid.dstPort = tcpHdr.DestinationPort()
|
||||
cid.proto = header.IPv6ProtocolNumber
|
||||
default:
|
||||
return cid, true
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue