TestEngineHappyPathInjectsAfterHandshake walks an SYN → SYN-ACK → ACK sequence and asserts the engine: - Accept-verdicts every observed packet - Injects exactly one fake ClientHello with wrong_seq - The injected packet parses, has valid checksums, and carries the SNI
(t *testing.T)
| 102 | // - Injects exactly one fake ClientHello with wrong_seq |
| 103 | // - The injected packet parses, has valid checksums, and carries the SNI |
| 104 | func TestEngineHappyPathInjectsAfterHandshake(t *testing.T) { |
| 105 | local := [4]byte{10, 0, 0, 1} |
| 106 | remote := [4]byte{1, 1, 1, 1} |
| 107 | const ( |
| 108 | localPort uint16 = 40000 |
| 109 | remotePort uint16 = 443 |
| 110 | synSeq uint32 = 0x1000 |
| 111 | synAckSeq uint32 = 0x9000 |
| 112 | ) |
| 113 | |
| 114 | be := newFakeBackend() |
| 115 | eng, err := New(Config{ |
| 116 | Strategy: bypass.NameWrongSeq, |
| 117 | SNIPool: []string{"auth.vercel.com"}, |
| 118 | InjectDelay: 5 * time.Millisecond, |
| 119 | Scope: platform.Scope{ |
| 120 | LocalIP: netip.AddrFrom4(local), |
| 121 | RemoteIP: netip.AddrFrom4(remote), |
| 122 | RemotePort: remotePort, |
| 123 | }, |
| 124 | }, be) |
| 125 | if err != nil { |
| 126 | t.Fatal(err) |
| 127 | } |
| 128 | |
| 129 | ctx, cancel := context.WithCancel(context.Background()) |
| 130 | defer cancel() |
| 131 | go eng.Run(ctx) |
| 132 | |
| 133 | var vc verdictCounter |
| 134 | send := func(dir platform.Direction, raw []byte) { |
| 135 | be.ch <- platform.Packet{Dir: dir, Raw: raw, Verdict: vc.fn()} |
| 136 | } |
| 137 | |
| 138 | // Outbound SYN. |
| 139 | send(platform.DirOutbound, makePkt(pktOpts{ |
| 140 | src: local, dst: remote, srcPort: localPort, dport: remotePort, |
| 141 | seq: synSeq, flags: flagSYN, |
| 142 | })) |
| 143 | // Inbound SYN-ACK. |
| 144 | send(platform.DirInbound, makePkt(pktOpts{ |
| 145 | src: remote, dst: local, srcPort: remotePort, dport: localPort, |
| 146 | seq: synAckSeq, ack: synSeq + 1, flags: flagSYN | flagACK, |
| 147 | })) |
| 148 | // Outbound ACK (completes handshake). |
| 149 | send(platform.DirOutbound, makePkt(pktOpts{ |
| 150 | src: local, dst: remote, srcPort: localPort, dport: remotePort, |
| 151 | seq: synSeq + 1, ack: synAckSeq + 1, flags: flagACK, |
| 152 | })) |
| 153 | |
| 154 | // Wait for the injected packet to land. |
| 155 | deadline := time.After(500 * time.Millisecond) |
| 156 | for { |
| 157 | if len(be.captured()) > 0 { |
| 158 | break |
| 159 | } |
| 160 | select { |
| 161 | case <-deadline: |
nothing calls this directly
no test coverage detected