File: 0002-Fix-max_time_t-overflow-error.patch

package info (click to toggle)
python-passlib 1.7.0-2
  • links: PTS, VCS
  • area: main
  • in suites: stretch
  • size: 3,172 kB
  • ctags: 3,873
  • sloc: python: 21,883; makefile: 5
file content (73 lines) | stat: -rw-r--r-- 2,826 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
From: Brian May <bam@debian.org>
Date: Sun, 23 Apr 2017 08:14:18 +1000
Subject: Fix max_time_t overflow error

Apply upstream patch from
https://bitbucket.org/ecollins/passlib/commits/80f838f5771f6753b0e46716ab25b48641aeef89

    passlib.tests.test_totp: fixed max_time_t calculation to trap some errors
    it was errorneously letting through; also workaround for python 3.6 issue
    29346.
---
 passlib/tests/test_totp.py | 48 +++++++++++++++++++++++++++++++++++++---------
 1 file changed, 39 insertions(+), 9 deletions(-)

diff --git a/passlib/tests/test_totp.py b/passlib/tests/test_totp.py
index 9af4d15..54a9d91 100644
--- a/passlib/tests/test_totp.py
+++ b/passlib/tests/test_totp.py
@@ -53,15 +53,45 @@ KEY4_RAW = b'Hello!\xde\xad\xbe\xef'
 assert sys.float_info.radix == 2, "unexpected float_info.radix"
 assert sys.float_info.mant_dig >= 44, "double precision unexpectedly small"
 
-# work out maximum value acceptable by hosts's time_t
-# this is frequently 2**37, though smaller on some systems.
-max_time_t = 30
-while True:
-    try:
-        datetime.datetime.utcfromtimestamp(max_time_t << 1)
-        max_time_t <<= 1
-    except ValueError:
-        break
+def _get_max_time_t():
+    """
+    helper to calc max_time_t constant (see below)
+    """
+    value = 1 << 30  # even for 32 bit systems will handle this
+    year = 0
+    while True:
+        next_value = value << 1
+        try:
+            next_year = datetime.datetime.utcfromtimestamp(next_value-1).year
+        except (ValueError, OSError, OverflowError):
+            # utcfromtimestamp() may throw any of the following:
+            #
+            # * year out of range for datetime:
+            #   py < 3.6 throws ValueError.
+            #   (py 3.6.0 returns odd value instead, see workaround below)
+            #
+            # * int out of range for host's gmtime/localtime:
+            #   py2 throws ValueError, py3 throws OSError.
+            #
+            # * int out of range for host's time_t:
+            #   py2 throws ValueError, py3 throws OverflowError.
+            #
+            return value-1
+
+        # Workaround for python 3.6.0 issue --
+        # Instead of throwing ValueError if year out of range for datetime,
+        # Python 3.6 will do some weird behavior that masks high bits
+        # e.g. (1<<40) -> year 36812, but (1<<41) -> year 6118.
+        # (Filed as bug -- http://bugs.python.org/issue29346)
+        # This check stops at largest non-wrapping bit size.
+        if next_year < year:
+            return value-1
+
+        value = next_value
+
+#: Rough approximation of max value acceptable by hosts's time_t.
+#: This is frequently ~2**37 on 64 bit, and ~2**31 on 32 bit systems.
+max_time_t = _get_max_time_t()
 
 def to_b32_size(raw_size):
     return (raw_size * 8 + 4) // 5