Skip to content

Commit cd74c27

Browse files
authored
Merge pull request #158 from EmperorGentoo/master
[agent] Work around for "ENHANCE_YOUR_CALM too_many_pings" errors that can be triggered by hosting provider's PING flood attack protections.
2 parents 05d659d + ef2ff8e commit cd74c27

File tree

1 file changed

+23
-1
lines changed

1 file changed

+23
-1
lines changed

agent/utils/utils.go

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -371,13 +371,35 @@ func postResponseWithRetries(client *http.Client, proxyURL, backendID, requestID
371371
}
372372
continue
373373
}
374+
// Force the response body to be fully read by copying it to the discard target.
375+
//
376+
// The response is expected to be empty for this specific case, so reading the entire
377+
// response body should be safe and not cause any delays.
378+
//
379+
// The reason we do this is because under certain conditions (in particular, when
380+
// using HTTP/2) the server and client might both try to close the underlying stream
381+
// at the same time. When that happens, the client sends a PING message at the
382+
// same time it sends the `RST_STREAM` message.
383+
//
384+
// If this happens a lot, it can trigger protections that a lot of server deployments
385+
// have against PING flood attacks.
386+
//
387+
// Draining the response body forces the server-side `END_STREAM` message to
388+
// arrive before the client tries to send the `RST_STREAM` message. In that case,
389+
// the client will not send a PING and so will not trigger these PING flood protections.
390+
//
391+
// A future version of the Go standard library will likely change the client behavior
392+
// so that it is more conservative about sending these PING messages, and if
393+
// that happens then this line can be removed. The proposed change for that
394+
// is https://go-review.git.corp.google.com/c/net/+/720300
395+
io.Copy(io.Discard, proxyResp.Body)
374396
proxyResp.Body.Close()
375397
if 500 <= proxyResp.StatusCode && proxyResp.StatusCode < 600 {
376398
if _, seekErr := proxyReadSeeker.Seek(0, io.SeekStart); seekErr != nil {
377399
return err
378400
}
379401
continue
380-
}
402+
}
381403
return nil
382404
}
383405
return err

0 commit comments

Comments
 (0)