Initial commit

This commit is contained in:
elisaveta9
2025-12-23 16:38:32 +03:00
commit b8f8e5607c
54 changed files with 2525 additions and 0 deletions
+82
View File
@@ -0,0 +1,82 @@
package ingress
import (
"log"
"net"
"relay/registry"
"relay/util"
tunnelpb "relay/proto/tunnel"
)
func handleClientTCP(conn net.Conn) {
defer conn.Close()
sni, hello, err := peekClientHello(conn)
if err != nil {
log.Println("peek failed:", err)
return
}
log.Println("Client SNI:", sni)
registry.Global.Mu.Lock()
dev := registry.Global.Domains[sni]
log.Println("Known domains:", util.Keys(registry.Global.Domains))
registry.Global.Mu.Unlock()
if dev == nil {
log.Println("No device bound for domain:", sni)
conn.Write([]byte("HTTP/1.1 503 No device\r\n\r\n"))
return
}
streamID := dev.AllocateStreamID()
done := dev.AddStream(streamID, conn)
log.Printf("Client [%s] → device (stream %d)\n", sni, streamID)
dev.SendFrame(&tunnelpb.Frame{
Type: tunnelpb.FrameType_FRAME_OPEN,
StreamId: streamID,
Payload: []byte(sni),
})
dev.SendFrame(&tunnelpb.Frame{
Type: tunnelpb.FrameType_FRAME_DATA,
StreamId: streamID,
Payload: hello,
})
go func() {
buf := util.BufPool.Get().([]byte)
defer util.BufPool.Put(buf)
for {
n, err := conn.Read(buf)
if err != nil {
dev.SendFrame(&tunnelpb.Frame{
Type: tunnelpb.FrameType_FRAME_CLOSE,
StreamId: streamID,
})
dev.RemoveStream(streamID)
return
}
dev.SendFrame(&tunnelpb.Frame{
Type: tunnelpb.FrameType_FRAME_DATA,
StreamId: streamID,
Payload: append([]byte(nil), buf[:n]...),
})
}
}()
select {
case <-done:
case <-dev.Done():
}
dev.RemoveStream(streamID)
}
+23
View File
@@ -0,0 +1,23 @@
package ingress
import (
"log"
"net"
)
func Listen(addr string) {
ln, err := net.Listen("tcp", addr)
if err != nil {
log.Fatal(err)
}
log.Println("HTTPS passthrough listening on", addr)
for {
c, err := ln.Accept()
if err != nil {
log.Println("accept error:", err)
continue
}
go handleClientTCP(c)
}
}
+73
View File
@@ -0,0 +1,73 @@
package ingress
import (
"bufio"
"encoding/binary"
"errors"
"io"
"strings"
)
func peekClientHello(r io.Reader) (sni string, hello []byte, err error) {
br := bufio.NewReader(r)
hdr, err := br.Peek(5)
if err != nil {
return "", nil, err
}
if hdr[0] != 0x16 {
return "", nil, errors.New("not TLS handshake")
}
recLen := int(binary.BigEndian.Uint16(hdr[3:5]))
total := 5 + recLen
hello, err = br.Peek(total)
if err != nil {
return "", nil, err
}
data := hello[5:]
if data[0] != 0x01 {
return "", hello, errors.New("not ClientHello")
}
i := 4
i += 2 + 32
sidLen := int(data[i])
i += 1 + sidLen
csLen := int(binary.BigEndian.Uint16(data[i:]))
i += 2 + csLen
compLen := int(data[i])
i += 1 + compLen
extLen := int(binary.BigEndian.Uint16(data[i:]))
i += 2
end := i + extLen
for i+4 <= end {
typ := binary.BigEndian.Uint16(data[i:])
sz := int(binary.BigEndian.Uint16(data[i+2:]))
i += 4
if typ == 0x00 {
l := int(binary.BigEndian.Uint16(data[i:]))
j := i + 2
for j+3 < i+l {
nameType := data[j]
nameLen := int(binary.BigEndian.Uint16(data[j+1:]))
if nameType == 0 {
sni = strings.ToLower(string(data[j+3 : j+3+nameLen]))
return sni, hello, nil
}
j += 3 + nameLen
}
}
i += sz
}
return "", hello, nil
}