Kaynağa Gözat

Merge pull request #359 from 9seconds/fix-android

Fix android ping
tags/v2.2.0^2^2
Sergei Arkhipov 1 ay önce
ebeveyn
işleme
a5d602b538
No account linked to committer's email address

+ 9
- 9
mtglib/internal/tls/fake/server_side.go Dosyayı Görüntüle

@@ -7,15 +7,17 @@ import (
7 7
 	"crypto/sha256"
8 8
 	"encoding/binary"
9 9
 	"io"
10
+	"math"
11
+	rnd "math/rand/v2"
10 12
 
13
+	"github.com/9seconds/mtg/v2/mtglib/internal/doppel"
11 14
 	"github.com/9seconds/mtg/v2/mtglib/internal/tls"
12 15
 	"golang.org/x/crypto/curve25519"
13 16
 )
14 17
 
15 18
 const (
16 19
 	TypeHandshakeServer = 0x02
17
-
18
-	ChangeCipherValue = 0x01
20
+	ChangeCipherValue   = 0x01
19 21
 
20 22
 	EllipticCurveLen = 32
21 23
 )
@@ -32,27 +34,24 @@ var serverHelloSuffix = []byte{
32 34
 	0x00, 0x20, // 32 bytes of key
33 35
 }
34 36
 
35
-func SendServerHello(w io.Writer, secret []byte, clientHello *ClientHello) ([]byte, error) {
37
+func SendServerHello(w io.Writer, secret []byte, clientHello *ClientHello) error {
36 38
 	buf := &bytes.Buffer{}
37 39
 	buf.Grow(tls.MaxRecordSize)
38 40
 
39 41
 	generateServerHello(buf, clientHello)
40 42
 	generateChangeCipherValue(buf)
41
-
42
-	noise := &bytes.Buffer{}
43
-	generateNoise(noise)
43
+	generateNoise(buf)
44 44
 
45 45
 	packet := buf.Bytes()
46 46
 	digest := hmac.New(sha256.New, secret)
47 47
 
48 48
 	digest.Write(clientHello.Random[:])
49 49
 	digest.Write(packet)
50
-	digest.Write(noise.Bytes())
51 50
 	copy(packet[RandomOffset:], digest.Sum(nil))
52 51
 
53 52
 	_, err := w.Write(packet)
54 53
 
55
-	return noise.Bytes()[tls.SizeHeader:], err
54
+	return err
56 55
 }
57 56
 
58 57
 func generateServerHello(buf *bytes.Buffer, hello *ClientHello) {
@@ -128,7 +127,8 @@ func generateChangeCipherValue(buf *bytes.Buffer) {
128 127
 }
129 128
 
130 129
 func generateNoise(buf *bytes.Buffer) {
131
-	data := [1369]byte{}
130
+	minSize := int(math.Round(0.75 * float64(doppel.TLSRecordSizeMax)))
131
+	data := make([]byte, minSize+rnd.IntN(doppel.TLSRecordSizeMax-minSize))
132 132
 
133 133
 	if _, err := rand.Read(data[:]); err != nil {
134 134
 		panic(err)

+ 12
- 14
mtglib/internal/tls/fake/server_side_test.go Dosyayı Görüntüle

@@ -8,6 +8,7 @@ import (
8 8
 	"testing"
9 9
 
10 10
 	"github.com/9seconds/mtg/v2/mtglib"
11
+	"github.com/9seconds/mtg/v2/mtglib/internal/doppel"
11 12
 	"github.com/9seconds/mtg/v2/mtglib/internal/tls"
12 13
 	"github.com/9seconds/mtg/v2/mtglib/internal/tls/fake"
13 14
 	"github.com/stretchr/testify/suite"
@@ -38,7 +39,7 @@ func (suite *SendServerHelloTestSuite) SetupTest() {
38 39
 }
39 40
 
40 41
 func (suite *SendServerHelloTestSuite) TestRecordStructure() {
41
-	noise, err := fake.SendServerHello(suite.buf, suite.secret.Key[:], suite.hello)
42
+	err := fake.SendServerHello(suite.buf, suite.secret.Key[:], suite.hello)
42 43
 	suite.NoError(err)
43 44
 
44 45
 	var rec bytes.Buffer
@@ -53,14 +54,18 @@ func (suite *SendServerHelloTestSuite) TestRecordStructure() {
53 54
 	suite.NoError(err)
54 55
 	suite.Equal(byte(tls.TypeChangeCipherSpec), recordType)
55 56
 
56
-	suite.Empty(suite.buf.Bytes())
57
+	rec.Reset()
57 58
 
58
-	// noise is raw payload without TLS record header
59
-	suite.Len(noise, 1369)
59
+	recordType, length, err := tls.ReadRecord(suite.buf, &rec)
60
+	suite.NoError(err)
61
+	suite.Equal(byte(tls.TypeApplicationData), recordType)
62
+	suite.Greater(length, int64(doppel.TLSRecordSizeStart))
63
+
64
+	suite.Empty(suite.buf.Bytes())
60 65
 }
61 66
 
62 67
 func (suite *SendServerHelloTestSuite) TestHMAC() {
63
-	noise, err := fake.SendServerHello(suite.buf, suite.secret.Key[:], suite.hello)
68
+	err := fake.SendServerHello(suite.buf, suite.secret.Key[:], suite.hello)
64 69
 	suite.NoError(err)
65 70
 
66 71
 	packet := make([]byte, suite.buf.Len())
@@ -74,18 +79,11 @@ func (suite *SendServerHelloTestSuite) TestHMAC() {
74 79
 	mac.Write(suite.hello.Random[:])
75 80
 	mac.Write(packet)
76 81
 
77
-	// HMAC is computed over the full noise TLS record (with header),
78
-	// but SendServerHello returns noise without the header,
79
-	// so we reconstruct the full record.
80
-	var fullNoise bytes.Buffer
81
-	tls.WriteRecord(&fullNoise, noise) //nolint: errcheck
82
-	mac.Write(fullNoise.Bytes())
83
-
84 82
 	suite.Equal(random, mac.Sum(nil))
85 83
 }
86 84
 
87 85
 func (suite *SendServerHelloTestSuite) TestHandshakePayload() {
88
-	_, err := fake.SendServerHello(suite.buf, suite.secret.Key[:], suite.hello)
86
+	err := fake.SendServerHello(suite.buf, suite.secret.Key[:], suite.hello)
89 87
 	suite.NoError(err)
90 88
 
91 89
 	packet := suite.buf.Bytes()
@@ -107,7 +105,7 @@ func (suite *SendServerHelloTestSuite) TestHandshakePayload() {
107 105
 }
108 106
 
109 107
 func (suite *SendServerHelloTestSuite) TestChangeCipherSpec() {
110
-	_, err := fake.SendServerHello(suite.buf, suite.secret.Key[:], suite.hello)
108
+	err := fake.SendServerHello(suite.buf, suite.secret.Key[:], suite.hello)
111 109
 	suite.NoError(err)
112 110
 
113 111
 	// Skip first record

+ 7
- 14
mtglib/proxy.go Dosyayı Görüntüle

@@ -78,8 +78,7 @@ func (p *Proxy) ServeConn(conn essentials.Conn) {
78 78
 		ctx.logger.Info("Stream has been finished")
79 79
 	}()
80 80
 
81
-	noise, ok := p.doFakeTLSHandshake(ctx)
82
-	if !ok {
81
+	if !p.doFakeTLSHandshake(ctx) {
83 82
 		return
84 83
 	}
85 84
 
@@ -90,11 +89,6 @@ func (p *Proxy) ServeConn(conn essentials.Conn) {
90 89
 	}
91 90
 	defer clientConn.Stop()
92 91
 
93
-	if _, err := clientConn.SyncWrite(noise); err != nil {
94
-		ctx.logger.InfoError("cannot send the first packet", err)
95
-		return
96
-	}
97
-
98 92
 	ctx.clientConn = clientConn
99 93
 
100 94
 	if err := p.doObfuscatedHandshake(ctx); err != nil {
@@ -176,7 +170,7 @@ func (p *Proxy) Shutdown() {
176 170
 	p.blocklist.Shutdown()
177 171
 }
178 172
 
179
-func (p *Proxy) doFakeTLSHandshake(ctx *streamContext) ([]byte, bool) {
173
+func (p *Proxy) doFakeTLSHandshake(ctx *streamContext) bool {
180 174
 	rewind := newConnRewind(ctx.clientConn)
181 175
 
182 176
 	clientHello, err := fake.ReadClientHello(
@@ -188,25 +182,24 @@ func (p *Proxy) doFakeTLSHandshake(ctx *streamContext) ([]byte, bool) {
188 182
 	if err != nil {
189 183
 		p.logger.InfoError("cannot read client hello", err)
190 184
 		p.doDomainFronting(ctx, rewind)
191
-		return nil, false
185
+		return false
192 186
 	}
193 187
 
194 188
 	if p.antiReplayCache.SeenBefore(clientHello.SessionID) {
195 189
 		p.logger.Warning("replay attack has been detected!")
196 190
 		p.eventStream.Send(p.ctx, NewEventReplayAttack(ctx.streamID))
197 191
 		p.doDomainFronting(ctx, rewind)
198
-		return nil, false
192
+		return false
199 193
 	}
200 194
 
201
-	noise, err := fake.SendServerHello(ctx.clientConn, p.secret.Key[:], clientHello)
202
-	if err != nil {
195
+	if err := fake.SendServerHello(ctx.clientConn, p.secret.Key[:], clientHello); err != nil {
203 196
 		p.logger.InfoError("cannot send welcome packet", err)
204
-		return nil, false
197
+		return false
205 198
 	}
206 199
 
207 200
 	ctx.clientConn = tls.New(ctx.clientConn, true, false)
208 201
 
209
-	return noise, true
202
+	return true
210 203
 }
211 204
 
212 205
 func (p *Proxy) doObfuscatedHandshake(ctx *streamContext) error {

Loading…
İptal
Kaydet