Golang TLS 问题

2022-02-15 23:52:03 +08:00
 yaott2020

用 Golang 写一个 TLS 隧道,不想验证域名(SNI),双向验证两端证书是否为同个 CA 证书签发,该如何实现。。

试过 VerifyPeerCertificate 但是在本地网络下可以运行,到了远程就报错,不知为何

路过大佬求点拨,以下是两端配置,谢谢。。。

======== Server ======== tlsConfig := tls.Config{} tlsConfig.InsecureSkipVerify = true tlsConfig.ClientAuth = tls.RequireAndVerifyClientCert tlsConfig.Certificates = []tls.Certificate{func() tls.Certificate { CertKey, err := tls.X509KeyPair(ServerCert, ServerKey) if err != nil { panic(err) } return CertKey }()} tlsConfig.VerifyPeerCertificate = func(rawCerts [][]byte, verifiedChains [][]*x509.Certificate) error { Roots := x509.NewCertPool() Roots.AppendCertsFromPEM(CA) cert, _ := x509.ParseCertificate(rawCerts[0]) opts := x509.VerifyOptions{ DNSName: "", Roots: Roots, } _, err := cert.Verify(opts) if err != nil { return err } return nil } ===== Client ===== tlsConfig := tls.Config{} tlsConfig.InsecureSkipVerify = true tlsConfig.Certificates = []tls.Certificate{func() tls.Certificate { CertKey, err := tls.X509KeyPair(ClientCert, ClientKey) if err != nil { panic(err) } return CertKey }()} tlsConfig.ClientAuth = tls.RequireAndVerifyClientCert tlsConfig.VerifyPeerCertificate = func(rawCerts [][]byte, verifiedChains [][]*x509.Certificate) error { Roots := x509.NewCertPool() Roots.AppendCertsFromPEM(CA) cert, _ := x509.ParseCertificate(rawCerts[0]) opts := x509.VerifyOptions{ DNSName: "", Roots: Roots, } _, err := cert.Verify(opts) if err != nil { return err } return nil }

2188 次点击
所在节点    Go 编程语言
7 条回复
yaott2020
2022-02-15 23:56:47 +08:00
我也不清楚为啥会这样,直接看图吧

https://imgtu.com/i/HW3T76
https://imgtu.com/i/HW3HAK
jinliming2
2022-02-16 09:25:55 +08:00
没做错误处理、自己处理一下
server 端:
cert, err := tls.LoadX509KeyPair(*cert, *key)

CA := x509.NewCertPool()
file, err := ioutil.ReadFile(*ca)
CA.AppendCertsFromPEM(file)

tlsConfig := tls.Config{
GetCertificate: func(info *tls.ClientHelloInfo) (*tls.Certificate, error) {
return &cert, nil
},
ClientAuth: tls.RequireAndVerifyClientCert,
ClientCAs: CA,
// ...
}

客户端:
cert, err := tls.LoadX509KeyPair(*cert, *key)

CA := x509.NewCertPool()
file, err := ioutil.ReadFile(*ca)
CA.AppendCertsFromPEM(file)

tlsConfig := tls.Config{
Certificates: []tls.Certificate{cert},
RootCAs: certPool,
ClientAuth: tls.RequireAndVerifyClientCert,
ClientCAs: certPool,
// ...
}
yaott2020
2022-02-16 12:54:42 +08:00
多谢,已解决
dzdh
2022-02-20 21:30:18 +08:00
@yaott2020 咋解决滴
yaott2020
2022-03-01 09:09:22 +08:00
服务器设置:
```
InsecureSkipVerify = false
Certificates //放服务器证书
ClientCAs //放 CA 证书
ClientAuth = tls.RequireAndVerifyClientCert
```

客户端设置:
```
InsecureSkipVerify = false
Certificates //放客户端证书
RootCAs //放 CA 证书
ServerName //设置 SNI ,必须与服务器证书的 servername 一致
```
yaott2020
2022-03-01 09:10:20 +08:00
客户端连接地址可以是域名可以是 ip ,反正会使用 ServerName 验证 SNI
yaott2020
2022-03-01 09:11:42 +08:00
服务器和客户端证书建议用同一个 CA 证书签发,(其他情况没试过)该配置可以实现双向验证

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

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

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

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

© 2021 V2EX