diff options
author | Andrew Lewis <nerf@judo.za.org> | 2024-05-27 12:05:53 +0200 |
---|---|---|
committer | Andrew Lewis <nerf@judo.za.org> | 2024-05-27 12:05:53 +0200 |
commit | 93b8af4f62ef8361864049e042dcf257371ec859 (patch) | |
tree | 543da4e08f3c21e0d83bced402735a5fd0ce16cb | |
parent | 08990def9860c586d9d9ec5a4e9865e3a9747aa4 (diff) | |
download | rspamd-93b8af4f62ef8361864049e042dcf257371ec859.tar.gz rspamd-93b8af4f62ef8361864049e042dcf257371ec859.zip |
[Rules] Added rules for detecting likely malware
-rw-r--r-- | conf/maps.d/exe_clickbait.inc | 15 | ||||
-rw-r--r-- | rules/archives.lua | 156 | ||||
-rw-r--r-- | rules/rspamd.lua | 1 |
3 files changed, 172 insertions, 0 deletions
diff --git a/conf/maps.d/exe_clickbait.inc b/conf/maps.d/exe_clickbait.inc new file mode 100644 index 000000000..b980ad79f --- /dev/null +++ b/conf/maps.d/exe_clickbait.inc @@ -0,0 +1,15 @@ +/\badvice\b/i +/\badvisory\b/i +/\baviso\b/i +/\bdocuments?\b/i +/\bcontract\b/i +/\bjustificante pago\b/i +/\bnotice\b/ +/\borden de litigio\b/i +/\border\b/i +/\bpago\b/i +/\bpayments?\b/i +/\bRFQ\b/ +/\bshipment\b/ +/\bshipping\b/ +/\bquotation\b/i diff --git a/rules/archives.lua b/rules/archives.lua new file mode 100644 index 000000000..83ac27df8 --- /dev/null +++ b/rules/archives.lua @@ -0,0 +1,156 @@ +local rspamd_regexp = require "rspamd_regexp" +local lua_maps = require "lua_maps" + +local clickbait_map = lua_maps.map_add_from_ucl( + { + string.format('%s/maps.d/%s', rspamd_paths.CONFDIR, 'exe_clickbait.inc'), + string.format('%s/local.d/maps.d/%s', rspamd_paths.LOCAL_CONFDIR, 'exe_clickbait.inc') + }, + 'regexp', + 'Inappropriate descriptions for executables' +) + +local exe_re = rspamd_regexp.create_cached([[/\.exe$|\.com$/i]]) +local img_re = rspamd_regexp.create_cached([[/\.img$/i]]) +local rar_re = rspamd_regexp.create_cached([[/\.rar$|\.r[0-9]{2}$/i]]) + +local id = rspamd_config:register_symbol{ + callback = function(task) + local num_checked = 0 + local have_subject_clickbait = false + + if clickbait_map:get_key(task:get_subject()) then + have_subject_clickbait = true + end + + for _, p in ipairs(task:get_parts()) do + local clickbait, exe, misidentified_rar = false, false, false + + if p:is_archive() then + num_checked = num_checked + 1 + local arc = p:get_archive() + local fn = p:get_filename() + + if clickbait_map:get_key(fn) ~= false then + clickbait = true + end + + if arc:get_type() == 'rar' then + if fn then + if not rar_re:match(fn) then + task:insert_result('MISIDENTIFIED_RAR', 1.0) + misidentified_rar = true + end + end + end + + local files = arc:get_files_full() + local max_check = math.min(#files, 10) + + for i = 1, max_check do + local info = files[i] + local name = info.name + + if img_re:match(name) then + local ratio = info.uncompressed_size/info.compressed_size + if ratio >= 500 then + task:insert_result('UDF_COMPRESSION_500PLUS', 1.0) + end + elseif exe_re:match(name) then + exe = true + task:insert_result('EXE_IN_ARCHIVE', 1.0) + if misidentified_rar then + task:insert_result('EXE_IN_MISIDENTIFIED_RAR', 1.0) + end + if clickbait then + task:insert_result('EXE_ARCHIVE_CLICKBAIT_FILENAME', 1.0) + elseif have_subject_clickbait then + task:insert_result('EXE_ARCHIVE_CLICKBAIT_SUBJECT', 1.0) + end + end + end + + if exe then + if #files == 1 then + task:insert_result('SINGLE_FILE_ARCHIVE_WITH_EXE', 1.0) + end + end + + if num_checked >= 10 then + return + end + end + end + end, + name = 'CHECK_ARCHIVES', + type = 'callback', +} + +rspamd_config:register_symbol{ + description = 'exe file in archive with clickbait filename', + group = 'malware', + name = 'EXE_ARCHIVE_CLICKBAIT_FILENAME', + one_shot = true, + parent = id, + score = 9.0, + type = 'virtual', +} + +rspamd_config:register_symbol{ + description = 'exe file in archive with clickbait subject', + group = 'malware', + name = 'EXE_ARCHIVE_CLICKBAIT_SUBJECT', + one_shot = true, + parent = id, + score = 9.0, + type = 'virtual', +} + +rspamd_config:register_symbol{ + description = 'exe file in archive', + group = 'malware', + name = 'EXE_IN_ARCHIVE', + one_shot = true, + parent = id, + score = 0.5, + type = 'virtual', +} + +rspamd_config:register_symbol{ + description = 'rar with wrong extension containing exe file', + group = 'malware', + name = 'EXE_IN_MISIDENTIFIED_RAR', + one_shot = true, + parent = id, + score = 2.0, + type = 'virtual', +} + +rspamd_config:register_symbol{ + description = 'rar with wrong extension', + group = 'malware', + name = 'MISIDENTIFIED_RAR', + one_shot = true, + parent = id, + score = 2.0, + type = 'virtual', +} + +rspamd_config:register_symbol{ + description = 'single file container bearing executable', + group = 'malware', + name = 'SINGLE_FILE_ARCHIVE_WITH_EXE', + one_shot = true, + parent = id, + score = 1.0, + type = 'virtual', +} + +rspamd_config:register_symbol{ + description = 'very well compressed img file in archive', + name = 'UDF_COMPRESSION_500PLUS', + one_shot = true, + parent = id, + score = 9.0, + type = 'virtual', +} diff --git a/rules/rspamd.lua b/rules/rspamd.lua index 6b2c1a51c..dcc872d15 100644 --- a/rules/rspamd.lua +++ b/rules/rspamd.lua @@ -25,6 +25,7 @@ local local_conf = rspamd_paths['LOCAL_CONFDIR'] local local_rules = rspamd_paths['RULESDIR'] local rspamd_util = require "rspamd_util" +dofile(local_rules .. '/archives.lua') dofile(local_rules .. '/regexp/headers.lua') dofile(local_rules .. '/regexp/misc.lua') dofile(local_rules .. '/regexp/upstream_spam_filters.lua') |