]> git.ipfire.org Git - thirdparty/freeradius-server.git/commitdiff
allow decoding part-way through a buffer
authorAlan T. DeKok <aland@freeradius.org>
Fri, 24 Sep 2021 18:37:26 +0000 (14:37 -0400)
committerAlan T. DeKok <aland@freeradius.org>
Tue, 28 Sep 2021 12:45:20 +0000 (08:45 -0400)
src/lib/util/dns.c
src/lib/util/dns.h
src/protocols/dhcpv6/decode.c

index 1ffdf35a72af1c3050430f6c4ce13eb1104e3d22..21efd63d509d8ba565af89e4fe1f4b779517fb67 100644 (file)
@@ -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.
index 525af1c24bc7f039e631577cead5bf124544e529..7dbbd9575d8c2c545a792aa193f9a2bf99d7e667 100644 (file)
@@ -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,
index a564e96a41a56bd20670d8070b550dd5166f4233..997a4000ffa261c8fa0e32ff81eb1f4687a3f3d1 100644 (file)
@@ -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);