From 7fc10c67dfdc8f2ab9a2e8abc4cd6bd2f8843c03 Mon Sep 17 00:00:00 2001 From: "Alan T. DeKok" Date: Fri, 24 Sep 2021 14:37:26 -0400 Subject: [PATCH] allow decoding part-way through a buffer --- src/lib/util/dns.c | 9 +++++---- src/lib/util/dns.h | 2 +- src/protocols/dhcpv6/decode.c | 2 +- 3 files changed, 7 insertions(+), 6 deletions(-) diff --git a/src/lib/util/dns.c b/src/lib/util/dns.c index 1ffdf35a72..21efd63d50 100644 --- a/src/lib/util/dns.c +++ b/src/lib/util/dns.c @@ -932,17 +932,18 @@ ssize_t fr_dns_label_uncompressed_length(uint8_t const *buf, size_t buf_len, uin * * @param[in] buf buffer holding one or more DNS labels * @param[in] buf_len total length of the buffer + * @param[in] start where to start looking * @return * - <=0 on error, where in the buffer the invalid label is located. * - > 0 total size of the encoded label(s). Will be <= buf_len */ -ssize_t fr_dns_labels_network_verify(uint8_t const *buf, size_t buf_len) +ssize_t fr_dns_labels_network_verify(uint8_t const *buf, size_t buf_len, uint8_t const *start) { ssize_t slen; - uint8_t const *label; + uint8_t const *label = start; uint8_t const *end = buf + buf_len; - for (label = buf; label < end; /* nothing */) { + while (label < end) { if (*label == 0x00) { label++; break; @@ -992,7 +993,7 @@ static ssize_t dns_label_decode(uint8_t const *buf, uint8_t const **start, uint8 * * The output type is always FR_TYPE_STRING * - * Note that the caller MUST call fr_dns_labels_network_verify(src, len) + * Note that the caller MUST call fr_dns_labels_network_verify(src, len, start) * before calling this function. Otherwise bad things will happen. * * @param[in] ctx Where to allocate any talloc buffers required. diff --git a/src/lib/util/dns.h b/src/lib/util/dns.h index 525af1c24b..7dbbd9575d 100644 --- a/src/lib/util/dns.h +++ b/src/lib/util/dns.h @@ -35,7 +35,7 @@ ssize_t fr_dns_label_uncompressed_length(uint8_t const *buf, size_t buf_len, ui ssize_t fr_dns_label_network_length(uint8_t const *buf, size_t buf_len); -ssize_t fr_dns_labels_network_verify(uint8_t const *buf, size_t buf_len); +ssize_t fr_dns_labels_network_verify(uint8_t const *buf, size_t buf_len, uint8_t const *start) CC_HINT(nonnull); ssize_t fr_dns_label_to_value_box(TALLOC_CTX *ctx, fr_value_box_t *dst, uint8_t const *src, size_t len, uint8_t const *label, diff --git a/src/protocols/dhcpv6/decode.c b/src/protocols/dhcpv6/decode.c index a564e96a41..997a4000ff 100644 --- a/src/protocols/dhcpv6/decode.c +++ b/src/protocols/dhcpv6/decode.c @@ -393,7 +393,7 @@ static ssize_t decode_dns_labels(TALLOC_CTX *ctx, fr_dcursor_t *cursor, fr_dict_ * If any of the labels point outside of this * area, OR they are otherwise invalid, then that's an error. */ - slen = fr_dns_labels_network_verify(data, data_len); + slen = fr_dns_labels_network_verify(data, data_len, data); if (slen < 0) { raw: return decode_raw(ctx, cursor, dict, parent, data, data_len, decode_ctx); -- 2.47.2