Files
anytls-go/cmd/server/main.go
2026-05-08 20:36:15 +08:00

120 lines
2.8 KiB
Go

package main
import (
"anytls/proxy/padding"
"anytls/util"
"context"
"crypto/sha256"
"crypto/tls"
"fmt"
"flag"
"io"
"net"
"os"
"strings"
"time"
"github.com/sirupsen/logrus"
)
var passwordSha256 []byte
func loadTLSCertificate(certFile string, keyFile string) (*tls.Certificate, error) {
if certFile == "" {
certFile = strings.TrimSpace(os.Getenv("ANYTLS_SERVER_CERT_FILE"))
}
if keyFile == "" {
keyFile = strings.TrimSpace(os.Getenv("ANYTLS_SERVER_KEY_FILE"))
}
if certFile == "" && keyFile == "" {
return nil, nil
}
if certFile == "" || keyFile == "" {
return nil, fmt.Errorf("both cert file and key file must be set")
}
cert, err := tls.LoadX509KeyPair(certFile, keyFile)
if err != nil {
return nil, err
}
return &cert, nil
}
func main() {
listen := flag.String("l", "0.0.0.0:8443", "server listen port")
password := flag.String("p", "", "password")
paddingScheme := flag.String("padding-scheme", "", "padding-scheme")
certFile := flag.String("cert-file", "", "tls certificate file path (PEM)")
keyFile := flag.String("key-file", "", "tls private key file path (PEM)")
flag.Parse()
if *password == "" {
logrus.Fatalln("please set password")
}
if *paddingScheme != "" {
if f, err := os.Open(*paddingScheme); err == nil {
b, err := io.ReadAll(f)
if err != nil {
logrus.Fatalln(err)
}
if padding.UpdatePaddingScheme(b) {
logrus.Infoln("loaded padding scheme file:", *paddingScheme)
} else {
logrus.Errorln("wrong format padding scheme file:", *paddingScheme)
}
f.Close()
} else {
logrus.Fatalln(err)
}
}
logLevel, err := logrus.ParseLevel(os.Getenv("LOG_LEVEL"))
if err != nil {
logLevel = logrus.InfoLevel
}
logrus.SetLevel(logLevel)
var sum = sha256.Sum256([]byte(*password))
passwordSha256 = sum[:]
logrus.Infoln("[Server]", util.ProgramVersionName)
logrus.Infoln("[Server] Listening TCP", *listen)
listener, err := net.Listen("tcp", *listen)
if err != nil {
logrus.Fatalln("listen server tcp:", err)
}
tlsCert, err := loadTLSCertificate(strings.TrimSpace(*certFile), strings.TrimSpace(*keyFile))
if err != nil {
logrus.Fatalln("load tls certificate:", err)
}
if tlsCert == nil {
tlsCert, err = util.GenerateKeyPair(time.Now, "")
if err != nil {
logrus.Fatalln("generate tls certificate:", err)
}
logrus.Infoln("[Server] Using generated ephemeral TLS certificate")
} else {
logrus.Infoln("[Server] Loaded TLS certificate from -cert-file/-key-file or ANYTLS_SERVER_CERT_FILE/ANYTLS_SERVER_KEY_FILE")
}
tlsConfig := &tls.Config{
GetCertificate: func(chi *tls.ClientHelloInfo) (*tls.Certificate, error) {
return tlsCert, nil
},
}
ctx := context.Background()
server := NewMyServer(tlsConfig)
for {
c, err := listener.Accept()
if err != nil {
logrus.Fatalln("accept:", err)
}
go handleTcpConnection(ctx, c, server)
}
}