gs should retry on SSL handshake timeout

BUG=chromium:657278
TEST=unittest

Change-Id: Idfdb3c49428641d906d377fc3f6861e437f544ef
Reviewed-on: https://chromium-review.googlesource.com/400622
Commit-Ready: Dan Shi <dshi@google.com>
Tested-by: Luigi Semenzato <semenzato@chromium.org>
Reviewed-by: Luigi Semenzato <semenzato@chromium.org>
(cherry picked from commit 5bdabc4cd926d2748b6413e3c4c398150b6fd01d)
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/chromite/+/2348686
Reviewed-by: Mike Frysinger <vapier@chromium.org>
Tested-by: Mike Frysinger <vapier@chromium.org>
diff --git a/lib/gs.py b/lib/gs.py
index 42f852e..e844e20 100644
--- a/lib/gs.py
+++ b/lib/gs.py
@@ -548,8 +548,9 @@
           'ResumableDownloadException',
           'ssl.SSLError: The read operation timed out',
           # TODO: Error messages may change in different library versions,
-          # use regexes to match resumbale error messages.
+          # use regexes to match resumable error messages.
           'ssl.SSLError: (\'The read operation timed out\',)',
+          'ssl.SSLError: _ssl.c:495: The handshake operation timed out',
           'Unable to find the server',
           'doesn\'t match cloud-supplied digest',
           'ssl.SSLError: [Errno 8]',
diff --git a/lib/gs_unittest.py b/lib/gs_unittest.py
index 44204f3..060bb6e 100644
--- a/lib/gs_unittest.py
+++ b/lib/gs_unittest.py
@@ -943,6 +943,12 @@
                            error)
     self.assertEqual(self.ctx._RetryFilter(e), True)
 
+  def testRetrySSLHandshakeTimeout(self):
+    """Verify retry behavior when handshake operation timed out."""
+    error = 'ssl.SSLError: _ssl.c:495: The handshake operation timed out'
+    e = self._getException(['gsutil', 'cp', self.REMOTE_PATH, self.LOCAL_PATH],
+                           error)
+    self.assertEqual(self.ctx._RetryFilter(e), True)
 
 class GSContextTest(AbstractGSContextTest):
   """Tests for GSContext()"""