如何用 golang 创建一个 https 服务用来获取来自浏览器的 tls 扩展信息?

2023-03-02 12:00:45 +08:00
 hygotest

我创建了一个类似这样的服务 package main

import ( "crypto/tls" "log" "net" )

func main() { cert, err := tls.LoadX509KeyPair("server.crt", "server.key") if err != nil { panic(err) }

tlsConfig := &tls.Config{
	// GetClientCertificate:     nil,
	PreferServerCipherSuites: true,
	CipherSuites: []uint16{
		tls.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
		tls.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384,
		tls.TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305,
	},
	MinVersion:             tls.VersionTLS12,
	CurvePreferences:       []tls.CurveID{tls.CurveP256, tls.CurveP384, tls.CurveP521},
	InsecureSkipVerify:     true,
	SessionTicketsDisabled: true,
	// ClientAuth:             tls.RequireAndVerifyClientCert,
	Certificates: []tls.Certificate{cert},
	ClientAuth:   tls.NoClientCert,
	GetCertificate: func(chi *tls.ClientHelloInfo) (*tls.Certificate, error) {
		return &cert, nil
	},
	GetClientCertificate: func(cri *tls.CertificateRequestInfo) (*tls.Certificate, error) {

		return &cert, nil
	},

	// GetConfigForClient: func(ch *tls.ClientHelloInfo) (*tls.Config, error) {
	// 	fmt.Println("GetConfigForClientHandler for:", ch.ServerName)
	// 	// ja3.ComputeJA3FromSegment(ch.Context())
	// 	return nil, nil
	// },
}
// tlsConfig := tls.Config{Certificates: []tls.Certificate{cert}}

listener, err := tls.Listen("tcp", ":8443", tlsConfig)
if err != nil {
	panic(err)
}
defer listener.Close()

for {
	conn, err := listener.Accept()
	if err != nil {
		log.Println(err)
		continue
	}
	go handleConnection(conn)
}

}

func handleConnection(conn net.Conn) { defer conn.Close()

buf := make([]byte, 4096)
for {
	n, err := conn.Read(buf)
	if err != nil {
		log.Println(err)
		return
	}
	log.Printf("Received %d bytes: %s", n, string(buf[:n]))
}

}

我想计算浏览器的 ja3 指纹,按照 ja3 的格式,其他信息都可以拿到,目前只有 tls extensions (类似 negetiaion_info,application_settings )这部份信息拿不到,看资料说是 tls 准备库不支持! 请问有没有其他办法拿到?

1125 次点击
所在节点    Go 编程语言
3 条回复
cqcsdzmt
2023-03-02 16:16:16 +08:00
if conn, ok := c.(*tls.Conn); ok {
for i, v := range conn.ConnectionState().PeerCertificates {
//edit: use %X for uppercase hex printing
log.Printf("cert %d sha1 fingerprint:%x \n", i, sha1.Sum(v.Raw))
}
}
hygotest
2023-03-02 17:05:24 +08:00
@cqcsdzmt

这个之前试过

peerCertificates:
[]*crypto/x509.Certificate len: 0, cap: 0, nil


但我证书是有效,而且我通过 wiresharke 抓包是可以获取这些 extensions list
hygotest
2023-03-02 17:12:54 +08:00
补充下,我想要的不是证书的指纹,而 tls 指纹

TLSVersion ,Ciphers ,Extensions ,EllipticCurves ,EllipticCurvePointFormats
目前 Extensions 这个字段里的信息拿不到!

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/920442

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX