]> dgit.raspbian.org Git - dovecot.git/commitdiff
[PATCH 11/14] lib-mail: Introduce struct message_part_data_limits and thread it throu...
authorTimo Sirainen <timo.sirainen@open-xchange.com>
Fri, 17 Apr 2026 13:54:48 +0000 (15:54 +0200)
committerNoah Meyerhans <noahm@debian.org>
Wed, 16 Sep 2026 19:06:35 +0000 (15:06 -0400)
Add an empty struct message_part_data_limits and pass it by pointer through
message_part_data_parse_from_header() and message_part_envelope_parse_from_header().

No behaviour change: the struct has no fields yet and no limits are applied.
Subsequent commits add the individual limit fields and enforcement.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Gbp-Pq: Name 0011-lib-mail-Introduce-struct-message_part_data_limits-a.patch

src/lib-imap/test-imap-bodystructure.c
src/lib-imap/test-imap-envelope.c
src/lib-mail/message-part-data.c
src/lib-mail/message-part-data.h
src/lib-mail/test-message-decoder.c
src/lib-mail/test-message-parser.c
src/lib-mail/test-message-part-data.c
src/lib-storage/index/index-mail-headers.c
src/lib-storage/index/index-mail.c
src/lib-storage/index/index-mail.h

index 40c8a8c6ecca371ed91036f3d9aff558adb065f7..abe35ac6f331dd2dee06c210995f848ed49796a3 100644 (file)
@@ -398,10 +398,11 @@ msg_parse(pool_t pool, const char *message, unsigned int max_nested_mime_parts,
 
        input = i_stream_create_from_data(message, strlen(message));
        parser = message_parser_init(pool, input, &parser_set);
+       struct message_part_data_limits limits = MESSAGE_PART_DATA_LIMITS_INIT;
        while ((ret = message_parser_parse_next_block(parser, &block)) > 0) {
                if (parse_bodystructure) {
                        message_part_data_parse_from_header(pool, block.part,
-                                                       block.hdr);
+                                                       &limits, block.hdr);
                }
        }
        test_assert(ret < 0);
index c9b92b4be2b42ad916225e13344a0d2288fa8e45..498c6ac9f44776083487e832a25db91e982253e5 100644 (file)
@@ -132,9 +132,11 @@ msg_parse(pool_t pool, const char *message)
 
        input = i_stream_create_from_data(message, strlen(message));
        parser = message_parser_init(pool, input, &parser_set);
+       struct message_part_data_limits limits = MESSAGE_PART_DATA_LIMITS_INIT;
        while ((ret = message_parser_parse_next_block(parser, &block)) > 0) {
                i_assert(block.part->parent == NULL);
-               message_part_envelope_parse_from_header(pool, &envlp, block.hdr);
+               message_part_envelope_parse_from_header(pool, &envlp, &limits,
+                                                       block.hdr);
        }
        test_assert(ret < 0);
 
index acd50e5210573394fa8f45ac5a7ca2ba9e29c124..c302fe568b5241cf23dc2415ec0472e3d3c0090e 100644 (file)
@@ -173,6 +173,7 @@ envelope_get_field(const char *name)
 
 void message_part_envelope_parse_from_header(pool_t pool,
        struct message_part_envelope **data,
+       struct message_part_data_limits *limits ATTR_UNUSED,
        struct message_header_line *hdr)
 {
        struct message_part_envelope *d;
@@ -480,6 +481,7 @@ parse_content_header(struct message_part_data *data,
 
 void message_part_data_parse_from_header(pool_t pool,
        struct message_part *part,
+       struct message_part_data_limits *limits,
        struct message_header_line *hdr)
 {
        struct message_part_data *part_data;
@@ -525,7 +527,8 @@ void message_part_data_parse_from_header(pool_t pool,
 
        if (parent_rfc822) {
                /* message/rfc822, we need the envelope */
-               message_part_envelope_parse_from_header(pool, &part_data->envelope, hdr);
+               message_part_envelope_parse_from_header(pool, &part_data->envelope,
+                                                       limits, hdr);
        }
 }
 
index 9513bfc2f01bebda81457656eff84bf71cf28637..1514f0daf2a0d20b5957cae3b9b9d45b7e623f6b 100644 (file)
@@ -8,6 +8,11 @@
 
 struct message_header_line;
 
+struct message_part_data_limits {
+};
+
+#define MESSAGE_PART_DATA_LIMITS_INIT { }
+
 struct message_part_param {
        const char *name;
        const char *value;
@@ -91,11 +96,13 @@ bool message_part_is_attachment(struct message_part *part,
 /* Update envelope data based from given header field */
 void message_part_envelope_parse_from_header(pool_t pool,
        struct message_part_envelope **_data,
+       struct message_part_data_limits *limits,
        struct message_header_line *hdr);
 
 /* Parse a single header. Note that this modifies part->context. */
 void message_part_data_parse_from_header(pool_t pool,
        struct message_part *part,
+       struct message_part_data_limits *limits,
        struct message_header_line *hdr);
 
 #endif
index 83c267187b3f1a4539a1bd4219b640f583f2f8fe..ad212c85465b482786672abb6461f498cc98a546 100644 (file)
@@ -260,8 +260,10 @@ static void test_message_decoder_content_transfer_encoding(void)
        parser = message_parser_init(pool, istream, &parser_set);
        decoder = message_decoder_init(NULL, 0);
 
+       struct message_part_data_limits limits = MESSAGE_PART_DATA_LIMITS_INIT;
        while ((ret = message_parser_parse_next_block(parser, &input)) > 0) {
-               message_part_data_parse_from_header(pool, input.part, input.hdr);
+               message_part_data_parse_from_header(pool, input.part, &limits,
+                                                   input.hdr);
                if (message_decoder_decode_next_block(decoder, &input, &output) &&
                    output.hdr == NULL && output.size > 0)
                        str_append_data(str_out, output.data, output.size);
@@ -349,8 +351,10 @@ static void test_message_decoder_invalid_content_transfer_encoding(void)
        parser = message_parser_init(pool, istream, &parser_set);
        decoder = message_decoder_init(NULL, 0);
 
+       struct message_part_data_limits limits = MESSAGE_PART_DATA_LIMITS_INIT;
        while ((ret = message_parser_parse_next_block(parser, &input)) > 0) {
-               message_part_data_parse_from_header(pool, input.part, input.hdr);
+               message_part_data_parse_from_header(pool, input.part, &limits,
+                                                   input.hdr);
                if (input.hdr != NULL &&
                    strcasecmp(input.hdr->name, "content-transfer-encoding") == 0) {
                        enum message_cte cte = message_decoder_parse_cte(input.hdr);
@@ -480,8 +484,10 @@ UNICODE_REPLACEMENT_CHAR_UTF8;
        parser = message_parser_init(pool, istream, &parser_set);
        decoder = message_decoder_init(NULL, 0);
 
+       struct message_part_data_limits limits = MESSAGE_PART_DATA_LIMITS_INIT;
        while ((ret = message_parser_parse_next_block(parser, &input)) > 0) {
-               message_part_data_parse_from_header(pool, input.part, input.hdr);
+               message_part_data_parse_from_header(pool, input.part, &limits,
+                                                   input.hdr);
                if (message_decoder_decode_next_block(decoder, &input, &output) &&
                    output.hdr == NULL && output.size > 0)
                        str_append_data(str_out, output.data, output.size);
@@ -531,8 +537,10 @@ static void test_message_decoder_charset_mime_part_change(void)
        parser = message_parser_init(pool, istream, &parser_set);
        decoder = message_decoder_init(NULL, 0);
 
+       struct message_part_data_limits limits = MESSAGE_PART_DATA_LIMITS_INIT;
        while ((ret = message_parser_parse_next_block(parser, &input)) > 0) {
-               message_part_data_parse_from_header(pool, input.part, input.hdr);
+               message_part_data_parse_from_header(pool, input.part, &limits,
+                                                   input.hdr);
                if (message_decoder_decode_next_block(decoder, &input, &output) &&
                    output.hdr == NULL && output.size > 0)
                        str_append_data(str_out, output.data, output.size);
index 3b94034c09f08517f8d197c47d74949773d6c73f..b66e0a664e77651d9e55a959cc2f440f2153a756 100644 (file)
@@ -51,12 +51,13 @@ static int message_parse_stream(pool_t pool, struct istream *input,
        struct message_parser_ctx *parser;
        struct message_block block;
 
+       struct message_part_data_limits limits = MESSAGE_PART_DATA_LIMITS_INIT;
        i_zero(&block);
        parser = message_parser_init(pool, input, set);
        while ((ret = message_parser_parse_next_block(parser, &block)) > 0)
                if (parse_data)
                        message_part_data_parse_from_header(pool, block.part,
-                                                           block.hdr);
+                                                           &limits, block.hdr);
        message_parser_deinit(&parser, parts_r);
        test_assert(input->stream_errno == 0);
        return ret;
index 470d739b5e6f4379a2cc14182c602a7968f38718..63228d1b3d9c3e36605b05d50fae59804aa734f7 100644 (file)
@@ -14,12 +14,13 @@ static int message_parse_stream(pool_t pool, struct istream *input,
        struct message_parser_ctx *parser;
        struct message_block block;
 
+       struct message_part_data_limits limits = MESSAGE_PART_DATA_LIMITS_INIT;
        i_zero(&block);
        parser = message_parser_init(pool, input, set);
        while ((ret = message_parser_parse_next_block(parser, &block)) > 0)
                if (parse_data)
                        message_part_data_parse_from_header(pool, block.part,
-                                                           block.hdr);
+                                                           &limits, block.hdr);
        message_parser_deinit(&parser, parts_r);
        test_assert(input->stream_errno == 0);
        return ret;
index a9f4d55c0d36cd3f5fefce0f51fd584cdf847c30..9d608acc61b53b4e13f9fa9a8a900cbd5af2f0dd 100644 (file)
@@ -308,12 +308,15 @@ void index_mail_parse_header(struct message_part *part,
        if (data->save_bodystructure_header &&
            !data->parsed_bodystructure_header) {
                i_assert(part != NULL);
-               message_part_data_parse_from_header(mail->mail.data_pool, part, hdr);
+               message_part_data_parse_from_header(mail->mail.data_pool, part,
+                                                   &mail->data.part_data_limits,
+                                                   hdr);
        }
 
        if (data->save_envelope) {
                message_part_envelope_parse_from_header(mail->mail.data_pool,
-                                          &data->envelope_data, hdr);
+                                          &data->envelope_data,
+                                          &mail->data.part_data_limits, hdr);
 
                if (hdr == NULL)
                         index_mail_parse_finish_imap_envelope(mail);
@@ -510,7 +513,8 @@ imap_envelope_parse_callback(struct message_header_line *hdr,
                             struct index_mail *mail)
 {
        message_part_envelope_parse_from_header(mail->mail.data_pool,
-                                  &mail->data.envelope_data, hdr);
+                                  &mail->data.envelope_data,
+                                  &mail->data.part_data_limits, hdr);
 
        if (hdr == NULL)
                index_mail_parse_finish_imap_envelope(mail);
index 70060ba4f75aaf37b0f62efcb0071444f1ab4244..3911f6db1c6a69a4ee32a507c1a689bbac591304 100644 (file)
@@ -696,11 +696,16 @@ void index_mail_cache_pop3_data(struct mail *_mail,
                                     &order, sizeof(order));
 }
 
+struct parse_bodystructure_ctx {
+       pool_t pool;
+       struct message_part_data_limits *limits;
+};
+
 static void parse_bodystructure_part_header(struct message_part *part,
                                            struct message_header_line *hdr,
-                                           pool_t pool)
+                                           struct parse_bodystructure_ctx *ctx)
 {
-       message_part_data_parse_from_header(pool, part, hdr);
+       message_part_data_parse_from_header(ctx->pool, part, ctx->limits, hdr);
 }
 
 static bool want_plain_bodystructure_cached(struct index_mail *mail)
@@ -1317,9 +1322,13 @@ static int index_mail_parse_body(struct index_mail *mail,
                /* bodystructure header is parsed, we want the body's mime
                   headers too */
                i_assert(data->parsed_bodystructure_header);
+               struct parse_bodystructure_ctx bsctx = {
+                       .pool = mail->mail.data_pool,
+                       .limits = &mail->data.part_data_limits,
+               };
                message_parser_parse_body(data->parser_ctx,
                                          parse_bodystructure_part_header,
-                                         mail->mail.data_pool);
+                                         &bsctx);
        } else {
                message_parser_parse_body(data->parser_ctx,
                        *null_message_part_header_callback, NULL);
@@ -1860,6 +1869,8 @@ static void index_mail_init_data(struct index_mail *mail)
        data->received_date = (time_t)-1;
        data->sent_date.time = (uint32_t)-1;
        data->dont_cache_field_idx = UINT_MAX;
+       data->part_data_limits = (struct message_part_data_limits)
+               MESSAGE_PART_DATA_LIMITS_INIT;
 
        data->wanted_fields = mail->mail.wanted_fields;
        if (mail->mail.wanted_headers != NULL) {
@@ -2321,7 +2332,9 @@ void index_mail_cache_parse_continue(struct mail *_mail)
                                mail->data.header_parsed = TRUE;
                } else {
                        message_part_data_parse_from_header(mail->mail.data_pool,
-                                                       block.part, block.hdr);
+                                                       block.part,
+                                                       &mail->data.part_data_limits,
+                                                       block.hdr);
                }
        }
 }
index 9e2159898e9820bc079f473016b19b401ec4e826..d1625b3f6e2e55f48bd361ec496d8e53c0a6b697 100644 (file)
@@ -2,6 +2,7 @@
 #define INDEX_MAIL_H
 
 #include "message-size.h"
+#include "message-part-data.h"
 #include "mail-cache.h"
 #include "mail-storage-private.h"
 
@@ -84,6 +85,7 @@ struct index_mail_data {
        const char *envelope, *body, *bodystructure, *guid, *filename;
        const char *from_envelope, *body_snippet;
        struct message_part_envelope *envelope_data;
+       struct message_part_data_limits part_data_limits;
 
        uint32_t cache_flags;
        uint64_t modseq, pvt_modseq;