Skip to content

Commit b0ea52b

Browse files
committed
strict error checking in DER decoding of integers and sequences
backport of 50e6d9f
1 parent bb359d3 commit b0ea52b

File tree

1 file changed

+21
-6
lines changed

1 file changed

+21
-6
lines changed

ecdsa/der.py

Lines changed: 21 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -60,10 +60,15 @@ def remove_constructed(string):
6060
return tag, body, rest
6161

6262
def remove_sequence(string):
63+
if not string:
64+
raise UnexpectedDER("Empty string does not encode a sequence")
6365
if not string.startswith(b("\x30")):
64-
n = string[0] if isinstance(string[0], integer_types) else ord(string[0])
65-
raise UnexpectedDER("wanted sequence (0x30), got 0x%02x" % n)
66+
n = string[0] if isinstance(string[0], integer_types) else \
67+
ord(string[0])
68+
raise UnexpectedDER("wanted type 'sequence' (0x30), got 0x%02x" % n)
6669
length, lengthlength = read_length(string[1:])
70+
if length > len(string) - 1 - lengthlength:
71+
raise UnexpectedDER("Length longer than the provided buffer")
6772
endseq = 1+lengthlength+length
6873
return string[1+lengthlength:endseq], string[endseq:]
6974

@@ -96,14 +101,24 @@ def remove_object(string):
96101
return tuple(numbers), rest
97102

98103
def remove_integer(string):
104+
if not string:
105+
raise UnexpectedDER("Empty string is an invalid encoding of an "
106+
"integer")
99107
if not string.startswith(b("\x02")):
100-
n = string[0] if isinstance(string[0], integer_types) else ord(string[0])
101-
raise UnexpectedDER("wanted integer (0x02), got 0x%02x" % n)
108+
n = string[0] if isinstance(string[0], integer_types) \
109+
else ord(string[0])
110+
raise UnexpectedDER("wanted type 'integer' (0x02), got 0x%02x" % n)
102111
length, llen = read_length(string[1:])
112+
if length > len(string) - 1 - llen:
113+
raise UnexpectedDER("Length longer than provided buffer")
114+
if length == 0:
115+
raise UnexpectedDER("0-byte long encoding of integer")
103116
numberbytes = string[1+llen:1+llen+length]
104117
rest = string[1+llen+length:]
105-
nbytes = numberbytes[0] if isinstance(numberbytes[0], integer_types) else ord(numberbytes[0])
106-
assert nbytes < 0x80 # can't support negative numbers yet
118+
nbytes = numberbytes[0] if isinstance(numberbytes[0], integer_types) \
119+
else ord(numberbytes[0])
120+
if not nbytes < 0x80:
121+
raise UnexpectedDER("Negative integers are not supported")
107122
return int(binascii.hexlify(numberbytes), 16), rest
108123

109124
def read_number(string):

0 commit comments

Comments
 (0)