8
8
9
9
namespace {
10
10
11
+ constexpr uint32_t INVALID = 0xFFFFFFFF ;
12
+
11
13
uint32_t DecodeBits (std::vector<bool >::const_iterator& bitpos, const std::vector<bool >::const_iterator& endpos, uint8_t minval, const std::vector<uint8_t > &bit_sizes)
12
14
{
13
15
uint32_t val = minval;
@@ -25,15 +27,15 @@ uint32_t DecodeBits(std::vector<bool>::const_iterator& bitpos, const std::vector
25
27
val += (1 << *bit_sizes_it);
26
28
} else {
27
29
for (int b = 0 ; b < *bit_sizes_it; b++) {
28
- if (bitpos == endpos) break ;
30
+ if (bitpos == endpos) return INVALID; // Reached EOF in mantissa
29
31
bit = *bitpos;
30
32
bitpos++;
31
33
val += bit << (*bit_sizes_it - 1 - b);
32
34
}
33
35
return val;
34
36
}
35
37
}
36
- return - 1 ;
38
+ return INVALID; // Reached EOF in exponent
37
39
}
38
40
39
41
enum class Instruction : uint32_t
@@ -83,9 +85,12 @@ uint32_t Interpret(const std::vector<bool> &asmap, const std::vector<bool> &ip)
83
85
while (pos != endpos) {
84
86
opcode = DecodeType (pos, endpos);
85
87
if (opcode == Instruction::RETURN) {
86
- return DecodeASN (pos, endpos);
88
+ default_asn = DecodeASN (pos, endpos);
89
+ if (default_asn == INVALID) break ; // ASN straddles EOF
90
+ return default_asn;
87
91
} else if (opcode == Instruction::JUMP) {
88
92
jump = DecodeJump (pos, endpos);
93
+ if (jump == INVALID) break ; // Jump offset straddles EOF
89
94
if (bits == 0 ) break ;
90
95
if (ip[ip.size () - bits]) {
91
96
if (jump >= endpos - pos) break ;
@@ -94,6 +99,7 @@ uint32_t Interpret(const std::vector<bool> &asmap, const std::vector<bool> &ip)
94
99
bits--;
95
100
} else if (opcode == Instruction::MATCH) {
96
101
match = DecodeMatch (pos, endpos);
102
+ if (match == INVALID) break ; // Match bits straddle EOF
97
103
matchlen = CountBits (match) - 1 ;
98
104
for (uint32_t bit = 0 ; bit < matchlen; bit++) {
99
105
if (bits == 0 ) break ;
@@ -104,8 +110,9 @@ uint32_t Interpret(const std::vector<bool> &asmap, const std::vector<bool> &ip)
104
110
}
105
111
} else if (opcode == Instruction::DEFAULT) {
106
112
default_asn = DecodeASN (pos, endpos);
113
+ if (default_asn == INVALID) break ; // ASN straddles EOF
107
114
} else {
108
- break ;
115
+ break ; // Instruction straddles EOF
109
116
}
110
117
}
111
118
return 0 ; // 0 is not a valid ASN
0 commit comments