github.com/Asutorufa/yuhaiin@v0.3.6-0.20240502055049-7984da7023a0/pkg/protos/node/point/point.go (about)

     1  package point
     2  
     3  import (
     4  	"crypto/tls"
     5  	"crypto/x509"
     6  	"errors"
     7  	"fmt"
     8  	"reflect"
     9  
    10  	"github.com/Asutorufa/yuhaiin/pkg/log"
    11  	"github.com/Asutorufa/yuhaiin/pkg/net/netapi"
    12  	protocol "github.com/Asutorufa/yuhaiin/pkg/protos/node/protocol"
    13  	"github.com/Asutorufa/yuhaiin/pkg/utils/syncmap"
    14  )
    15  
    16  func init() {
    17  	RegisterProtocol(func(*protocol.Protocol_None) WrapProxy {
    18  		return func(p netapi.Proxy) (netapi.Proxy, error) { return p, nil }
    19  	})
    20  }
    21  
    22  func Dialer(p *Point) (r netapi.Proxy, err error) {
    23  	r = bootstrapProxy
    24  
    25  	for _, v := range p.Protocols {
    26  		r, err = Wrap(v.Protocol)(r)
    27  		if err != nil {
    28  			return
    29  		}
    30  	}
    31  
    32  	return
    33  }
    34  
    35  type WrapProxy func(p netapi.Proxy) (netapi.Proxy, error)
    36  
    37  var execProtocol syncmap.SyncMap[reflect.Type, func(protocol.IsProtocol_Protocol) WrapProxy]
    38  
    39  func RegisterProtocol[T protocol.IsProtocol_Protocol](wrap func(T) WrapProxy) {
    40  	if wrap == nil {
    41  		return
    42  	}
    43  
    44  	var z T
    45  	execProtocol.Store(
    46  		reflect.TypeOf(z),
    47  		func(t protocol.IsProtocol_Protocol) WrapProxy { return wrap(t.(T)) },
    48  	)
    49  }
    50  
    51  func Wrap(p protocol.IsProtocol_Protocol) WrapProxy {
    52  	if p == nil {
    53  		return ErrConn(fmt.Errorf("value is nil: %v", p))
    54  	}
    55  
    56  	conn, ok := execProtocol.Load(reflect.TypeOf(p))
    57  	if !ok {
    58  		return ErrConn(fmt.Errorf("protocol %v is not support", p))
    59  	}
    60  
    61  	return conn(p)
    62  }
    63  
    64  var tlsSessionCache = tls.NewLRUClientSessionCache(128)
    65  
    66  func ParseTLSConfig(t *protocol.TlsConfig) *tls.Config {
    67  	if t == nil || !t.Enable {
    68  		return nil
    69  	}
    70  
    71  	root, err := x509.SystemCertPool()
    72  	if err != nil {
    73  		log.Error("get x509 system cert pool failed, create new cert pool.", "err", err)
    74  		root = x509.NewCertPool()
    75  	}
    76  
    77  	for i := range t.CaCert {
    78  		ok := root.AppendCertsFromPEM(t.CaCert[i])
    79  		if !ok {
    80  			log.Error("add cert from pem failed.")
    81  		}
    82  	}
    83  
    84  	var servername string
    85  	if len(t.ServerNames) > 0 {
    86  		servername = t.ServerNames[0]
    87  	}
    88  
    89  	return &tls.Config{
    90  		ServerName:         servername,
    91  		RootCAs:            root,
    92  		NextProtos:         t.NextProtos,
    93  		InsecureSkipVerify: t.InsecureSkipVerify,
    94  		ClientSessionCache: tlsSessionCache,
    95  		// SessionTicketsDisabled: true,
    96  	}
    97  }
    98  
    99  func ErrConn(err error) WrapProxy {
   100  	return func(netapi.Proxy) (netapi.Proxy, error) {
   101  		return nil, err
   102  	}
   103  }
   104  
   105  var bootstrapProxy = netapi.NewErrProxy(errors.New("bootstrap proxy"))
   106  
   107  func IsBootstrap(p netapi.Proxy) bool { return p == bootstrapProxy }
   108  
   109  func SetBootstrap(p netapi.Proxy) {
   110  	if p == nil {
   111  		return
   112  	}
   113  
   114  	bootstrapProxy = p
   115  }