authorgravatar for 124872+jedisct1@users.noreply.github.comFrank Denis <124872+jedisct1@users.noreply.github.com> 2021-08-09 22:44:23+02:00
committergravatar for noreply@github.comGitHub <noreply@github.com> 2021-08-09 22:44:23+02:00
log2ccd023c6ae590b4ff311814ccf5ff508c7669ef
tree6d3e420271225b5e5d22bf8f1d1e9666d8eb01e8
parent799fedf612aa8742c446b015c12d21707a1dbec0
signaturebadge-question-mark Signed by PGP key 4AEE18F83AFDEB23

Ip4Address parser: reject 0-prefixed components (#9538)

Some parsers interpret these as octal, some don't, and the confusion can lead to vulnerabilities. Return error.NonCanonical when parsing IPv4 addresses with 0 prefixes.

2 files changed, 11 insertions(+), 0 deletions(-)

lib/std/net.zig+10
......@@ -34,6 +34,7 @@ pub const Address = extern union {
3434 error.InvalidEnd,
3535 error.InvalidCharacter,
3636 error.Incomplete,
37 error.NonCanonical,
3738 => {},
3839 }
3940
......@@ -55,6 +56,7 @@ pub const Address = extern union {
5556 error.InvalidEnd,
5657 error.InvalidCharacter,
5758 error.Incomplete,
59 error.NonCanonical,
5860 => {},
5961 }
6062
......@@ -204,6 +206,7 @@ pub const Ip4Address = extern struct {
204206 var x: u8 = 0;
205207 var index: u8 = 0;
206208 var saw_any_digits = false;
209 var has_zero_prefix = false;
207210 for (buf) |c| {
208211 if (c == '.') {
209212 if (!saw_any_digits) {
......@@ -216,7 +219,13 @@ pub const Ip4Address = extern struct {
216219 index += 1;
217220 x = 0;
218221 saw_any_digits = false;
222 has_zero_prefix = false;
219223 } else if (c >= '0' and c <= '9') {
224 if (c == '0' and !saw_any_digits) {
225 has_zero_prefix = true;
226 } else if (has_zero_prefix) {
227 return error.NonCanonical;
228 }
220229 saw_any_digits = true;
221230 x = try std.math.mul(u8, x, 10);
222231 x = try std.math.add(u8, x, c - '0');
......@@ -1149,6 +1158,7 @@ fn linuxLookupNameFromHosts(
11491158 error.Incomplete,
11501159 error.InvalidIPAddressFormat,
11511160 error.InvalidIpv4Mapping,
1161 error.NonCanonical,
11521162 => continue,
11531163 };
11541164 try addrs.append(LookupAddr{ .addr = addr });
lib/std/net/test.zig+1
......@@ -92,6 +92,7 @@ test "parse and render IPv4 addresses" {
9292 try testing.expectError(error.InvalidEnd, net.Address.parseIp4("127.0.0.1.1", 0));
9393 try testing.expectError(error.Incomplete, net.Address.parseIp4("127.0.0.", 0));
9494 try testing.expectError(error.InvalidCharacter, net.Address.parseIp4("100..0.1", 0));
95 try testing.expectError(error.NonCanonical, net.Address.parseIp4("127.01.0.1", 0));
9596}
9697
9798test "resolve DNS" {