-
Notifications
You must be signed in to change notification settings - Fork 18k
net/http: EOF during TLS handshake #61721
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
You could use |
Please change the title to I feel like an EOF can't be ignored here, but hard to say without knowing the context to reproduce this. Likely the connection was refused for a reason, maybe the client asked for a protocol that the server does not support. If possible share the Go version you are using alongside with a reproducible test case. |
Changed title. Yes that will work too - err != nil && err != io.EOF Here is an example to run the server on https://localhost:8300/test - open a new browser session after starting the server as it only happens on handshake not when opening a new browser tab after hitting the url create a certificates folder and add in there a ca.crt, localhost.crt and localhost.key that you can generate on your end
|
I think it might have to do with the ciphers being offered by the client (browser in this case). If I try to access the page with firefox I also get the EOF. If I try to offer a supported cipher there is no EOF error: |
If you add all ciphers still gets an EOF. What is Firefox, Chrome, Edge sending as cipher and what client cert they send? var Ciphers = []uint16{
} |
@golang/security @neild |
I also have the same problem occur. |
We have a similar symptom/issue, although a different scenario when we try to do mtls with I'm not sure if I should open a different issue for this, so I'll post reproduction steps here. This happens on go versions How to create a certificate on the key card:
Demo
Go server code:
Edit: Seems like its exclusive to |
Oh, Thanks. First of all, the questions I have are: Cause of the problem: Posted below are the extensions. extensions: 10 items |
I have also experienced something similar to #61721 (comment) I started encountering Forcing the Max TLS to 1.2, which these connections were previously using, solved this issue. But it would be nice to look into this if it is a known client behaviour that the tls server connection implementation for TLS 1.3 in golang should be able to handle. edit: we now have more information about our particular case in #70232 |
I experienced something very similar to the previous two comments. I started encountering EOF errors during tls.Conn.Handshake() for connections from outlook.com when they were using TLS 1.3. Forcing the max TLS to 1.2 solved this issue. |
This is an old issue but I am adding my two cents as well. Seems a lot of proxies struggle with TLS1.3 and forcing TLS 1.2 did the trick for me after hours of battling with the client. Including my HTTP Client code for anyone that this might help. // CreateHTTPClient creates an HTTP client with proxy support from environment
func CreateHTTPClient(cfg config.HttpClientConfig) *http.Client {
// Load system CA certificates
caCertPool, err := x509.SystemCertPool()
if err != nil {
log.Printf("Failed to load system cert pool: %v, using empty pool", err)
// Fall back to an empy cert pool if system certs cant be loaded
caCertPool = x509.NewCertPool()
}
log.Printf("Using system CA certificates")
transport := &http.Transport{
TLSClientConfig: &tls.Config{
MinVersion: tls.VersionTLS12, // Force TLS 1.2
MaxVersion: tls.VersionTLS12,
RootCAs: caCertPool,
// Optional: Set InsecureSkipVerify to true temporarily for debugging
// InsecureSkipVerify: true, // Uncomment only for debugging, not production
},
DialContext: (&net.Dialer{
Timeout: 30 * time.Second,
KeepAlive: 30 * time.Second,
}).DialContext,
TLSHandshakeTimeout: 10 * time.Second,
MaxIdleConns: 1,
IdleConnTimeout: 0,
}
// Use environment variables for proxy configuration
transport.Proxy = func(req *http.Request) (*url.URL, error) {
proxyURL, err := http.ProxyFromEnvironment(req)
if err != nil {
log.Printf("Error determining proxy from environment: %v", err)
return nil, err
}
if proxyURL != nil {
log.Printf("Using proxy for %s: %s", req.URL.Host, proxyURL.String())
} else {
log.Printf("No proxy used for %s (NO_PROXY: %s)", req.URL.Host, os.Getenv("NO_PROXY"))
}
return proxyURL, nil
}
// If you need to handle proxy authentication, you can add it here
// We'll check for PROXY_USER and PROXY_PASS environment variables
proxyUser := os.Getenv("PROXY_USER")
proxyPass := os.Getenv("PROXY_PASS")
if proxyUser != "" && proxyPass != "" {
transport.ProxyConnectHeader = http.Header{
"Proxy-Authorization": []string{
"Basic " + base64.StdEncoding.EncodeToString(
[]byte(proxyUser+":"+proxyPass),
),
},
}
}
// Configure HTTP/2
if err := http2.ConfigureTransport(transport); err != nil {
log.Printf("Failed to configure HTTP/2 transport: %v", err)
}
return &http.Client{
Transport: transport,
Timeout: cfg.Timeout,
}
} |
Looking at all these reports, I think they're all issues on the opposite end not properly implementing TLS 1.3. |
The reported EOF error, happens when tls.ClientAuth is set to tls.VerifyClientCertIfGiven - if no certificate is provided or request comes from any browser it throws this error, and it should not given that only if Cert if given, unless there is a way to setup the browser to send a specific client cert?
File - /src/net/http/server.go
Current version -
Propose Fix - tested on my environment - add this to the if line - && err.Error() != "EOF"
The text was updated successfully, but these errors were encountered: