diff options
author | Vsevolod Stakhov <vsevolod@highsecure.ru> | 2016-12-16 17:56:55 +0000 |
---|---|---|
committer | Vsevolod Stakhov <vsevolod@highsecure.ru> | 2016-12-16 17:56:55 +0000 |
commit | da7970857f420b4598e62f424e99f6d87a0035a3 (patch) | |
tree | b1e445da6e153025befe4a436e0a90aff08d6851 /src/libmime | |
parent | 98ef56b2b103b07f7678cc47cd0ccbb0a48c5616 (diff) | |
download | rspamd-da7970857f420b4598e62f424e99f6d87a0035a3.tar.gz rspamd-da7970857f420b4598e62f424e99f6d87a0035a3.zip |
[Rework|Minor] Further fixes for the new mime parser
Diffstat (limited to 'src/libmime')
-rw-r--r-- | src/libmime/archives.c | 119 | ||||
-rw-r--r-- | src/libmime/archives.h | 2 | ||||
-rw-r--r-- | src/libmime/images.c | 71 | ||||
-rw-r--r-- | src/libmime/images.h | 5 | ||||
-rw-r--r-- | src/libmime/message.c | 18 | ||||
-rw-r--r-- | src/libmime/mime_encoding.c | 2 | ||||
-rw-r--r-- | src/libmime/mime_expressions.c | 191 |
7 files changed, 147 insertions, 261 deletions
diff --git a/src/libmime/archives.c b/src/libmime/archives.c index 501f2a4a3..c78b8c976 100644 --- a/src/libmime/archives.c +++ b/src/libmime/archives.c @@ -18,6 +18,7 @@ #include "message.h" #include "task.h" #include "archives.h" +#include "fstring.h" static void rspamd_archive_dtor (gpointer p) @@ -51,8 +52,8 @@ rspamd_archive_process_zip (struct rspamd_task *task, struct rspamd_archive_file *f; /* Zip files have interesting data at the end of archive */ - p = part->content->data + part->content->len - 1; - start = part->content->data; + p = part->parsed_data.begin + part->parsed_data.len - 1; + start = part->parsed_data.begin; end = p; /* Search for EOCD: @@ -78,13 +79,13 @@ rspamd_archive_process_zip (struct rspamd_task *task, if (eocd == NULL) { /* Not a zip file */ - msg_debug_task ("zip archive is invalid (no EOCD): %s", part->filename); + msg_debug_task ("zip archive is invalid (no EOCD)"); return; } if (end - eocd < 21) { - msg_debug_task ("zip archive is invalid (short EOCD): %s", part->filename); + msg_debug_task ("zip archive is invalid (short EOCD)"); return; } @@ -97,8 +98,7 @@ rspamd_archive_process_zip (struct rspamd_task *task, /* We need to check sanity as well */ if (cd_offset + cd_size != (guint)(eocd - start)) { - msg_debug_task ("zip archive is invalid (bad size/offset for CD): %s", - part->filename); + msg_debug_task ("zip archive is invalid (bad size/offset for CD)"); return; } @@ -115,8 +115,7 @@ rspamd_archive_process_zip (struct rspamd_task *task, /* Read central directory record */ if (eocd - cd < cd_basic_len || memcmp (cd, cd_magic, sizeof (cd_magic)) != 0) { - msg_debug_task ("zip archive is invalid (bad cd record): %s", - part->filename); + msg_debug_task ("zip archive is invalid (bad cd record)"); return; } @@ -133,8 +132,7 @@ rspamd_archive_process_zip (struct rspamd_task *task, comment_len = GUINT16_FROM_LE (comment_len); if (cd + fname_len + comment_len + extra_len + cd_basic_len > eocd) { - msg_debug_task ("zip archive is invalid (too large cd record): %s", - part->filename); + msg_debug_task ("zip archive is invalid (too large cd record)"); return; } @@ -150,9 +148,13 @@ rspamd_archive_process_zip (struct rspamd_task *task, } part->flags |= RSPAMD_MIME_PART_ARCHIVE; - part->specific_data = arch; - arch->archive_name = part->filename; - arch->size = part->content->len; + part->specific.arch = arch; + + if (part->cd) { + arch->archive_name = &part->cd->filename; + } + + arch->size = part->parsed_data.len; } static inline gint @@ -197,11 +199,11 @@ rspamd_archive_rar_read_vint (const guchar *start, gsize remain, guint64 *res) #define RAR_SKIP_BYTES(n) do { \ if ((n) <= 0) { \ - msg_debug_task ("rar archive is invalid (bad skip value): %s", part->filename); \ + msg_debug_task ("rar archive is invalid (bad skip value)"); \ return; \ } \ if ((gsize)(end - p) < (n)) { \ - msg_debug_task ("rar archive is invalid (truncated): %s", part->filename); \ + msg_debug_task ("rar archive is invalid (truncated)"); \ return; \ } \ p += (n); \ @@ -210,11 +212,11 @@ rspamd_archive_rar_read_vint (const guchar *start, gsize remain, guint64 *res) #define RAR_READ_VINT() do { \ r = rspamd_archive_rar_read_vint (p, end - p, &vint); \ if (r == -1) { \ - msg_debug_task ("rar archive is invalid (bad vint): %s", part->filename); \ + msg_debug_task ("rar archive is invalid (bad vint)"); \ return; \ } \ else if (r == 0) { \ - msg_debug_task ("rar archive is invalid (BAD vint offset): %s", part->filename); \ + msg_debug_task ("rar archive is invalid (BAD vint offset)"); \ return; \ }\ } while (0) @@ -222,7 +224,7 @@ rspamd_archive_rar_read_vint (const guchar *start, gsize remain, guint64 *res) #define RAR_READ_VINT_SKIP() do { \ r = rspamd_archive_rar_read_vint (p, end - p, &vint); \ if (r == -1) { \ - msg_debug_task ("rar archive is invalid (bad vint): %s", part->filename); \ + msg_debug_task ("rar archive is invalid (bad vint)"); \ return; \ } \ p += r; \ @@ -230,7 +232,7 @@ rspamd_archive_rar_read_vint (const guchar *start, gsize remain, guint64 *res) #define RAR_READ_UINT16(n) do { \ if (end - p < (glong)sizeof (guint16)) { \ - msg_debug_task ("rar archive is invalid (bad int16): %s", part->filename); \ + msg_debug_task ("rar archive is invalid (bad int16)"); \ return; \ } \ n = p[0] + (p[1] << 8); \ @@ -239,7 +241,7 @@ rspamd_archive_rar_read_vint (const guchar *start, gsize remain, guint64 *res) #define RAR_READ_UINT32(n) do { \ if (end - p < (glong)sizeof (guint32)) { \ - msg_debug_task ("rar archive is invalid (bad int32): %s", part->filename); \ + msg_debug_task ("rar archive is invalid (bad int32)"); \ return; \ } \ n = p[0] + (p[1] << 8) + (p[2] << 16) + (p[3] << 24); \ @@ -293,8 +295,7 @@ rspamd_archive_process_rar_v4 (struct rspamd_task *task, const guchar *start, if (sz == 0) { /* Zero sized block - error */ - msg_debug_task ("rar archive is invalid (zero size block): %s", - part->filename); + msg_debug_task ("rar archive is invalid (zero size block)"); return; } @@ -310,7 +311,7 @@ rspamd_archive_process_rar_v4 (struct rspamd_task *task, const guchar *start, RAR_READ_UINT16 (fname_len); if (fname_len == 0 || fname_len > (gsize)(end - p)) { - msg_debug_task ("rar archive is invalid (bad fileame size): %s", part->filename); + msg_debug_task ("rar archive is invalid (bad fileame size)"); return; } @@ -367,9 +368,9 @@ rspamd_archive_process_rar_v4 (struct rspamd_task *task, const guchar *start, end: part->flags |= RSPAMD_MIME_PART_ARCHIVE; - part->specific_data = arch; - arch->archive_name = part->filename; - arch->size = part->content->len; + part->specific.arch = arch; + arch->archive_name = &part->cd->filename; + arch->size = part->parsed_data.len; } static void @@ -386,11 +387,11 @@ rspamd_archive_process_rar (struct rspamd_task *task, struct rspamd_archive_file *f; gint r; - p = part->content->data; - end = p + part->content->len; + p = part->parsed_data.begin; + end = p + part->parsed_data.len; if ((gsize)(end - p) <= sizeof (rar_v5_magic)) { - msg_debug_task ("rar archive is invalid (too small): %s", part->filename); + msg_debug_task ("rar archive is invalid (too small)"); return; } @@ -405,7 +406,7 @@ rspamd_archive_process_rar (struct rspamd_task *task, return; } else { - msg_debug_task ("rar archive is invalid (no rar magic): %s", part->filename); + msg_debug_task ("rar archive is invalid (no rar magic)"); return; } @@ -447,8 +448,7 @@ rspamd_archive_process_rar (struct rspamd_task *task, goto end; } else if (type != rar_main_header) { - msg_debug_task ("rar archive is invalid (bad main header): %s", - part->filename); + msg_debug_task ("rar archive is invalid (bad main header)"); return; } @@ -467,8 +467,7 @@ rspamd_archive_process_rar (struct rspamd_task *task, sz = vint; if (sz == 0) { /* Zero sized block - error */ - msg_debug_task ("rar archive is invalid (zero size block): %s", - part->filename); + msg_debug_task ("rar archive is invalid (zero size block)"); return; } @@ -528,7 +527,7 @@ rspamd_archive_process_rar (struct rspamd_task *task, fname_len = vint; if (fname_len == 0 || fname_len > (gsize)(end - p)) { - msg_debug_task ("rar archive is invalid (bad fileame size): %s", part->filename); + msg_debug_task ("rar archive is invalid (bad fileame size)"); return; } @@ -546,45 +545,51 @@ rspamd_archive_process_rar (struct rspamd_task *task, } end: - part->flags |= RSPAMD_MIME_PART_ARCHIVE; - part->specific_data = arch; - arch->archive_name = part->filename; - arch->size = part->content->len; +part->flags |= RSPAMD_MIME_PART_ARCHIVE; + part->specific.arch = arch; + if (part->cd != NULL) { + arch->archive_name = &part->cd->filename; + } + arch->size = part->parsed_data.len; } static gboolean rspamd_archive_cheat_detect (struct rspamd_mime_part *part, const gchar *str, const guchar *magic_start, gsize magic_len) { - GMimeContentType *ct; - const gchar *fname, *p; + struct rspamd_content_type *ct; + const gchar *p; + rspamd_ftok_t srch, *fname; - ct = part->type; + ct = part->ct; + RSPAMD_FTOK_ASSIGN (&srch, "application"); - if (ct && ct->type && ct->subtype && strcmp (ct->type, - "application") == 0) { - if (rspamd_substring_search_caseless (ct->subtype, strlen (ct->subtype), + if (ct && ct->type.len && ct->subtype.len > 0 && rspamd_ftok_cmp (&ct->type, + &srch) == 0) { + if (rspamd_substring_search_caseless (ct->subtype.begin, ct->subtype.len, str, strlen (str)) != -1) { return TRUE; } } - fname = part->filename; + if (part->cd) { + fname = &part->cd->filename; - if (fname && strlen (fname) > strlen (str)) { - p = fname + strlen (fname) - strlen (str); + if (fname && fname->len > strlen (str)) { + p = fname->begin + fname->len - strlen (str); - if (rspamd_lc_cmp (p, str, strlen (str)) == 0) { - if (*(p - 1) == '.') { - return TRUE; + if (rspamd_lc_cmp (p, str, strlen (str)) == 0) { + if (*(p - 1) == '.') { + return TRUE; + } } } - } - if (magic_start != NULL) { - if (part->content->len > magic_len && memcmp (part->content->data, - magic_start, magic_len) == 0) { - return TRUE; + if (magic_start != NULL) { + if (part->parsed_data.len > magic_len && memcmp (part->parsed_data.begin, + magic_start, magic_len) == 0) { + return TRUE; + } } } @@ -602,7 +607,7 @@ rspamd_archives_process (struct rspamd_task *task) for (i = 0; i < task->parts->len; i ++) { part = g_ptr_array_index (task->parts, i); - if (part->content->len > 0) { + if (part->parsed_data.len > 0) { if (rspamd_archive_cheat_detect (part, "zip", zip_magic, sizeof (zip_magic))) { rspamd_archive_process_zip (task, part); diff --git a/src/libmime/archives.h b/src/libmime/archives.h index d6d474486..9b64ab130 100644 --- a/src/libmime/archives.h +++ b/src/libmime/archives.h @@ -40,7 +40,7 @@ struct rspamd_archive_file { struct rspamd_archive { enum rspamd_archive_type type; - const gchar *archive_name; + const rspamd_ftok_t *archive_name; gsize size; enum rspamd_archive_flags flags; GPtrArray *files; /* Array of struct rspamd_archive_file */ diff --git a/src/libmime/images.c b/src/libmime/images.c index a0b9c30d5..d6532b4fe 100644 --- a/src/libmime/images.c +++ b/src/libmime/images.c @@ -43,11 +43,14 @@ rspamd_images_process (struct rspamd_task *task) { guint i; struct rspamd_mime_part *part; + rspamd_ftok_t srch; + + RSPAMD_FTOK_ASSIGN (&srch, "image"); for (i = 0; i < task->parts->len; i ++) { part = g_ptr_array_index (task->parts, i); - if (g_mime_content_type_is_type (part->type, "image", "*") && - part->content->len > 0) { + if (rspamd_ftok_cmp (&part->ct->type, &srch) == 0 && + part->parsed_data.len > 0) { process_image (task, part); } } @@ -55,28 +58,28 @@ rspamd_images_process (struct rspamd_task *task) } static enum rspamd_image_type -detect_image_type (GByteArray *data) +detect_image_type (rspamd_ftok_t *data) { if (data->len > sizeof (png_signature) / sizeof (png_signature[0])) { - if (memcmp (data->data, png_signature, sizeof (png_signature)) == 0) { + if (memcmp (data->begin, png_signature, sizeof (png_signature)) == 0) { return IMAGE_TYPE_PNG; } } if (data->len > 10) { - if (memcmp (data->data, jpg_sig1, sizeof (jpg_sig1)) == 0) { - if (memcmp (data->data + 2, jpg_sig_jfif, sizeof (jpg_sig_jfif)) == 0 || - memcmp (data->data + 2, jpg_sig_exif, sizeof (jpg_sig_exif)) == 0) { + if (memcmp (data->begin, jpg_sig1, sizeof (jpg_sig1)) == 0) { + if (memcmp (data->begin + 2, jpg_sig_jfif, sizeof (jpg_sig_jfif)) == 0 || + memcmp (data->begin + 2, jpg_sig_exif, sizeof (jpg_sig_exif)) == 0) { return IMAGE_TYPE_JPG; } } } if (data->len > sizeof (gif_signature) / sizeof (gif_signature[0])) { - if (memcmp (data->data, gif_signature, sizeof (gif_signature)) == 0) { + if (memcmp (data->begin, gif_signature, sizeof (gif_signature)) == 0) { return IMAGE_TYPE_GIF; } } if (data->len > sizeof (bmp_signature) / sizeof (bmp_signature[0])) { - if (memcmp (data->data, bmp_signature, sizeof (bmp_signature)) == 0) { + if (memcmp (data->begin, bmp_signature, sizeof (bmp_signature)) == 0) { return IMAGE_TYPE_BMP; } } @@ -86,11 +89,11 @@ detect_image_type (GByteArray *data) static struct rspamd_image * -process_png_image (struct rspamd_task *task, GByteArray *data) +process_png_image (struct rspamd_task *task, rspamd_ftok_t *data) { struct rspamd_image *img; guint32 t; - guint8 *p; + const guint8 *p; if (data->len < 24) { msg_info_task ("bad png detected (maybe striped)"); @@ -99,7 +102,7 @@ process_png_image (struct rspamd_task *task, GByteArray *data) /* In png we should find iHDR section and get data from it */ /* Skip signature and read header section */ - p = data->data + 12; + p = data->begin + 12; if (memcmp (p, "IHDR", 4) != 0) { msg_info_task ("png doesn't begins with IHDR section"); return NULL; @@ -120,9 +123,9 @@ process_png_image (struct rspamd_task *task, GByteArray *data) } static struct rspamd_image * -process_jpg_image (struct rspamd_task *task, GByteArray *data) +process_jpg_image (struct rspamd_task *task, rspamd_ftok_t *data) { - guint8 *p, *end; + const guint8 *p, *end; guint16 h, w; struct rspamd_image *img; @@ -130,7 +133,7 @@ process_jpg_image (struct rspamd_task *task, GByteArray *data) img->type = IMAGE_TYPE_JPG; img->data = data; - p = data->data; + p = data->begin; end = p + data->len - 8; p += 2; @@ -163,10 +166,10 @@ process_jpg_image (struct rspamd_task *task, GByteArray *data) } static struct rspamd_image * -process_gif_image (struct rspamd_task *task, GByteArray *data) +process_gif_image (struct rspamd_task *task, rspamd_ftok_t *data) { struct rspamd_image *img; - guint8 *p; + const guint8 *p; guint16 t; if (data->len < 10) { @@ -178,7 +181,7 @@ process_gif_image (struct rspamd_task *task, GByteArray *data) img->type = IMAGE_TYPE_GIF; img->data = data; - p = data->data + 6; + p = data->begin + 6; memcpy (&t, p, sizeof (guint16)); img->width = GUINT16_FROM_LE (t); memcpy (&t, p + 2, sizeof (guint16)); @@ -188,11 +191,11 @@ process_gif_image (struct rspamd_task *task, GByteArray *data) } static struct rspamd_image * -process_bmp_image (struct rspamd_task *task, GByteArray *data) +process_bmp_image (struct rspamd_task *task, rspamd_ftok_t *data) { struct rspamd_image *img; gint32 t; - guint8 *p; + const guint8 *p; if (data->len < 28) { msg_info_task ("bad bmp detected (maybe striped)"); @@ -202,7 +205,7 @@ process_bmp_image (struct rspamd_task *task, GByteArray *data) img = rspamd_mempool_alloc0 (task->task_pool, sizeof (struct rspamd_image)); img->type = IMAGE_TYPE_BMP; img->data = data; - p = data->data + 18; + p = data->begin + 18; memcpy (&t, p, sizeof (gint32)); img->width = abs (GINT32_FROM_LE (t)); memcpy (&t, p + 4, sizeof (gint32)); @@ -448,16 +451,16 @@ rspamd_image_normalize (struct rspamd_task *task, struct rspamd_image *img) switch (img->type) { case IMAGE_TYPE_JPG: - src = gdImageCreateFromJpegPtr (img->data->len, img->data->data); + src = gdImageCreateFromJpegPtr (img->data->len, (void *)img->data->begin); break; case IMAGE_TYPE_PNG: - src = gdImageCreateFromPngPtr (img->data->len, img->data->data); + src = gdImageCreateFromPngPtr (img->data->len, (void *)img->data->begin); break; case IMAGE_TYPE_GIF: - src = gdImageCreateFromGifPtr (img->data->len, img->data->data); + src = gdImageCreateFromGifPtr (img->data->len, (void *)img->data->begin); break; case IMAGE_TYPE_BMP: - src = gdImageCreateFromBmpPtr (img->data->len, img->data->data); + src = gdImageCreateFromBmpPtr (img->data->len, (void *)img->data->begin); break; default: return; @@ -560,19 +563,19 @@ process_image (struct rspamd_task *task, struct rspamd_mime_part *part) guint cid_len, i, j; GPtrArray *ar; - if ((type = detect_image_type (part->content)) != IMAGE_TYPE_UNKNOWN) { + if ((type = detect_image_type (&part->parsed_data)) != IMAGE_TYPE_UNKNOWN) { switch (type) { case IMAGE_TYPE_PNG: - img = process_png_image (task, part->content); + img = process_png_image (task, &part->parsed_data); break; case IMAGE_TYPE_JPG: - img = process_jpg_image (task, part->content); + img = process_jpg_image (task, &part->parsed_data); break; case IMAGE_TYPE_GIF: - img = process_gif_image (task, part->content); + img = process_gif_image (task, &part->parsed_data); break; case IMAGE_TYPE_BMP: - img = process_bmp_image (task, part->content); + img = process_bmp_image (task, &part->parsed_data); break; default: img = NULL; @@ -585,7 +588,11 @@ process_image (struct rspamd_task *task, struct rspamd_mime_part *part) rspamd_image_type_str (img->type), img->width, img->height, task->message_id); - img->filename = part->filename; + + if (part->cd) { + img->filename = &part->cd->filename; + } + img->parent = part; if (img->data->len <= task->cfg->max_pic_size) { @@ -596,7 +603,7 @@ process_image (struct rspamd_task *task, struct rspamd_mime_part *part) img->filename, img->data->len); } part->flags |= RSPAMD_MIME_PART_IMAGE; - part->specific_data = img; + part->specific.img = img; /* Check Content-Id */ ar = rspamd_message_get_header_from_hash (part->raw_headers, diff --git a/src/libmime/images.h b/src/libmime/images.h index 1ad73f69e..e442eaa40 100644 --- a/src/libmime/images.h +++ b/src/libmime/images.h @@ -2,6 +2,7 @@ #define IMAGES_H_ #include "config.h" +#include "fstring.h" struct html_image; struct rspamd_task; @@ -19,8 +20,8 @@ enum rspamd_image_type { struct rspamd_image { struct rspamd_mime_part *parent; - GByteArray *data; - const gchar *filename; + rspamd_ftok_t *data; + rspamd_ftok_t *filename; struct html_image *html_image; enum rspamd_image_type type; guint32 width; diff --git a/src/libmime/message.c b/src/libmime/message.c index 0d5ea98c0..4626950f9 100644 --- a/src/libmime/message.c +++ b/src/libmime/message.c @@ -584,7 +584,6 @@ rspamd_message_parse (struct rspamd_task *task) GPtrArray *hdrs; struct rspamd_mime_header *rh; struct rspamd_mime_text_part *p1, *p2; - struct mime_foreach_data md; struct received_header *recv, *trecv; const gchar *p; gsize len; @@ -650,16 +649,12 @@ rspamd_message_parse (struct rspamd_task *task) if (!rspamd_mime_parse_task (task, &err)) { msg_err_task ("cannot construct mime from stream: %e", err); - if (err) { - g_error_free (err); - } if (task->cfg && (!task->cfg->allow_raw_input)) { msg_err_task ("cannot construct mime from stream"); - g_set_error (&task->err, - rspamd_message_quark (), - RSPAMD_FILTER_ERROR, \ + if (err) { + task->err = err; + } - "cannot parse MIME in the message"); return FALSE; } else { @@ -670,7 +665,7 @@ rspamd_message_parse (struct rspamd_task *task) else { GString str; - str.str = p; + str.str = (gchar *)p; str.len = len; hdr_pos = rspamd_string_find_eoh (&str, &body_pos); @@ -707,9 +702,6 @@ rspamd_message_parse (struct rspamd_task *task) task->message_id = "undef"; } - memset (&md, 0, sizeof (md)); - md.task = task; - debug_task ("found %ud parts in message", task->parts->len); if (task->queue_id == NULL) { task->queue_id = "undef"; @@ -833,7 +825,7 @@ rspamd_message_parse (struct rspamd_task *task) hdrs = rspamd_message_get_header_array (task, to_hdrs[k], FALSE); if (hdrs && hdrs->len > 0) { - InternetAddress *tia; + InternetAddressList *tia; for (i = 0; i < hdrs->len; i ++) { rh = g_ptr_array_index (hdrs, i); diff --git a/src/libmime/mime_encoding.c b/src/libmime/mime_encoding.c index 5629e1ee4..6790cd8e6 100644 --- a/src/libmime/mime_encoding.c +++ b/src/libmime/mime_encoding.c @@ -209,7 +209,7 @@ rspamd_mime_text_part_maybe_convert (struct rspamd_task *task, GByteArray *result_array, *part_content; struct rspamd_mime_part *part = text_part->mime_part; - part_content = rspamd_mempool_alloc0 (sizeof (GByteArray)); + part_content = rspamd_mempool_alloc0 (task->task_pool, sizeof (GByteArray)); part_content->data = (guint8 *)text_part->parsed.begin; part_content->len = text_part->parsed.len; diff --git a/src/libmime/mime_expressions.c b/src/libmime/mime_expressions.c index 928949e8a..582c38d2d 100644 --- a/src/libmime/mime_expressions.c +++ b/src/libmime/mime_expressions.c @@ -1326,18 +1326,8 @@ rspamd_is_recipients_sorted (struct rspamd_task * task, void *unused) { /* Check all types of addresses */ - if (is_recipient_list_sorted (g_mime_message_get_recipients (task->message, - GMIME_RECIPIENT_TYPE_TO)) == TRUE) { - return TRUE; - } - if (is_recipient_list_sorted (g_mime_message_get_recipients (task->message, - GMIME_RECIPIENT_TYPE_BCC)) == TRUE) { - return TRUE; - } - if (is_recipient_list_sorted (g_mime_message_get_recipients (task->message, - GMIME_RECIPIENT_TYPE_CC)) == TRUE) { - return TRUE; - } + + /* TODO: fix this function */ return FALSE; } @@ -1654,76 +1644,9 @@ rspamd_content_type_compare_param (struct rspamd_task * task, GArray * args, void *unused) { - const gchar *param_name; - const gchar *param_data; - rspamd_regexp_t *re; - struct expression_argument *arg, *arg1, *arg_pattern; - GMimeObject *part; - GMimeContentType *ct; - gint r; - guint i; - gboolean recursive = FALSE; - struct rspamd_mime_part *cur_part; - - if (args == NULL || args->len < 2) { - msg_warn_task ("no parameters to function"); - return FALSE; - } - - arg = &g_array_index (args, struct expression_argument, 0); - g_assert (arg->type == EXPRESSION_ARGUMENT_NORMAL); - param_name = arg->data; - arg_pattern = &g_array_index (args, struct expression_argument, 1); - - for (i = 0; i < task->parts->len; i ++) { - cur_part = g_ptr_array_index (task->parts, i); - part = cur_part->mime; - ct = (GMimeContentType *)g_mime_object_get_content_type (part); - - if (args->len >= 3) { - arg1 = &g_array_index (args, struct expression_argument, 2); - if (g_ascii_strncasecmp (arg1->data, "true", - sizeof ("true") - 1) == 0) { - recursive = TRUE; - } - } - else { - /* - * If user did not specify argument, let's assume that he wants - * recursive search if mime part is multipart/mixed - */ - if (g_mime_content_type_is_type (ct, "multipart", "*")) { - recursive = TRUE; - } - } -#ifndef GMIME24 - g_object_unref (part); -#endif - if ((param_data = - g_mime_content_type_get_parameter ((GMimeContentType *)ct, - param_name)) != NULL) { - if (arg_pattern->type == EXPRESSION_ARGUMENT_REGEXP) { - re = arg_pattern->data; - r = rspamd_regexp_search (re, param_data, 0, - NULL, NULL, FALSE, NULL); - - if (r) { - return TRUE; - } - } - else { - /* Just do strcasecmp */ - if (g_ascii_strcasecmp (param_data, arg_pattern->data) == 0) { - return TRUE; - } - } - } - /* Get next part */ - if (!recursive) { - break; - } - } + /* TODO: fix */ + msg_err_task ("content_type_compare_param is broken XXX"); return FALSE; } @@ -1733,61 +1656,10 @@ rspamd_content_type_has_param (struct rspamd_task * task, GArray * args, void *unused) { - gchar *param_name; - const gchar *param_data; - struct expression_argument *arg, *arg1; - GMimeObject *part; - GMimeContentType *ct; - gboolean recursive = FALSE, result = FALSE; - guint i; - struct rspamd_mime_part *cur_part; - - if (args == NULL || args->len < 1) { - msg_warn_task ("no parameters to function"); - return FALSE; - } - - arg = &g_array_index (args, struct expression_argument, 0); - g_assert (arg->type == EXPRESSION_ARGUMENT_NORMAL); - param_name = arg->data; - - for (i = 0; i < task->parts->len; i ++) { - cur_part = g_ptr_array_index (task->parts, i); - part = cur_part->mime; - ct = (GMimeContentType *)g_mime_object_get_content_type (part); - - if (args->len >= 2) { - arg1 = &g_array_index (args, struct expression_argument, 2); - if (g_ascii_strncasecmp (arg1->data, "true", - sizeof ("true") - 1) == 0) { - recursive = TRUE; - } - } - else { - /* - * If user did not specify argument, let's assume that he wants - * recursive search if mime part is multipart/mixed - */ - if (g_mime_content_type_is_type (ct, "multipart", "*")) { - recursive = TRUE; - } - } - -#ifndef GMIME24 - g_object_unref (part); -#endif - if ((param_data = - g_mime_content_type_get_parameter ((GMimeContentType *)ct, - param_name)) != NULL) { - return TRUE; - } - /* Get next part */ - if (!recursive) { - break; - } - } + /* TODO: fix */ + msg_err_task ("content_type_compare_param is broken XXX"); - return result; + return FALSE; } static gboolean @@ -1795,11 +1667,10 @@ rspamd_content_type_check (struct rspamd_task *task, GArray * args, gboolean check_subtype) { - const gchar *param_data; + rspamd_ftok_t *param_data, srch; rspamd_regexp_t *re; struct expression_argument *arg1, *arg_pattern; - GMimeObject *part; - GMimeContentType *ct; + struct rspamd_content_type *ct; gint r; guint i; gboolean recursive = FALSE; @@ -1814,8 +1685,7 @@ rspamd_content_type_check (struct rspamd_task *task, for (i = 0; i < task->parts->len; i ++) { cur_part = g_ptr_array_index (task->parts, i); - part = cur_part->mime; - ct = (GMimeContentType *)g_mime_object_get_content_type (part); + ct = cur_part->ct; if (args->len >= 2) { arg1 = &g_array_index (args, struct expression_argument, 1); @@ -1829,7 +1699,7 @@ rspamd_content_type_check (struct rspamd_task *task, * If user did not specify argument, let's assume that he wants * recursive search if mime part is multipart/mixed */ - if (g_mime_content_type_is_type (ct, "multipart", "*")) { + if (IS_CT_MULTIPART (ct)) { recursive = TRUE; } } @@ -1838,15 +1708,15 @@ rspamd_content_type_check (struct rspamd_task *task, g_object_unref (part); #endif if (check_subtype) { - param_data = ct->subtype; + param_data = &ct->subtype; } else { - param_data = ct->type; + param_data = &ct->type; } if (arg_pattern->type == EXPRESSION_ARGUMENT_REGEXP) { re = arg_pattern->data; - r = rspamd_regexp_search (re, param_data, 0, + r = rspamd_regexp_search (re, param_data->begin, param_data->len, NULL, NULL, FALSE, NULL); if (r) { @@ -1855,7 +1725,10 @@ rspamd_content_type_check (struct rspamd_task *task, } else { /* Just do strcasecmp */ - if (g_ascii_strcasecmp (param_data, arg_pattern->data) == 0) { + srch.begin = arg_pattern->data; + srch.len = strlen (arg_pattern->data); + + if (rspamd_ftok_casecmp (param_data, &srch) == 0) { return TRUE; } } @@ -1886,10 +1759,11 @@ rspamd_content_type_is_subtype (struct rspamd_task * task, } static gboolean -compare_subtype (struct rspamd_task *task, GMimeContentType * ct, +compare_subtype (struct rspamd_task *task, struct rspamd_content_type *ct, struct expression_argument *subtype) { rspamd_regexp_t *re; + rspamd_ftok_t srch; gint r = 0; if (subtype == NULL || ct == NULL) { @@ -1898,12 +1772,15 @@ compare_subtype (struct rspamd_task *task, GMimeContentType * ct, } if (subtype->type == EXPRESSION_ARGUMENT_REGEXP) { re = subtype->data; - r = rspamd_regexp_search (re, ct->subtype, 0, + r = rspamd_regexp_search (re, ct->subtype.begin, ct->subtype.len, NULL, NULL, FALSE, NULL); } else { + srch.begin = subtype->data; + srch.len = strlen (subtype->data); + /* Just do strcasecmp */ - if (ct->subtype && g_ascii_strcasecmp (ct->subtype, subtype->data) == 0) { + if (rspamd_ftok_casecmp (&ct->subtype, &srch) == 0) { return TRUE; } } @@ -1919,13 +1796,13 @@ compare_len (struct rspamd_mime_part *part, guint min, guint max) } if (min == 0) { - return part->content->len <= max; + return part->parsed_data.len <= max; } else if (max == 0) { - return part->content->len >= min; + return part->parsed_data.len >= min; } else { - return part->content->len >= min && part->content->len <= max; + return part->parsed_data.len >= min && part->parsed_data.len <= max; } } @@ -1938,13 +1815,14 @@ common_has_content_part (struct rspamd_task * task, { rspamd_regexp_t *re; struct rspamd_mime_part *part; - GMimeContentType *ct; + struct rspamd_content_type *ct; + rspamd_ftok_t srch; gint r; guint i; for (i = 0; i < task->parts->len; i ++) { part = g_ptr_array_index (task->parts, i); - ct = part->type; + ct = part->ct; if (ct == NULL) { continue; @@ -1953,7 +1831,7 @@ common_has_content_part (struct rspamd_task * task, if (param_type->type == EXPRESSION_ARGUMENT_REGEXP) { re = param_type->data; - r = rspamd_regexp_search (re, ct->type, 0, + r = rspamd_regexp_search (re, ct->type.begin, ct->type.len, NULL, NULL, FALSE, NULL); /* Also check subtype and length of the part */ if (r && param_subtype) { @@ -1965,7 +1843,10 @@ common_has_content_part (struct rspamd_task * task, } else { /* Just do strcasecmp */ - if (ct->type && g_ascii_strcasecmp (ct->type, param_type->data) == 0) { + srch.begin = param_type->data; + srch.len = strlen (param_type->data); + + if (rspamd_ftok_casecmp (&ct->type, &srch) == 0) { if (param_subtype) { if (compare_subtype (task, ct, param_subtype)) { if (compare_len (part, min_len, max_len)) { |