From c53dd6be7203038a0be6e73f1eb4beeeecd65b91 Mon Sep 17 00:00:00 2001 From: Steve Freegard Date: Thu, 23 Mar 2017 21:27:02 +0000 Subject: New rules --- rules/misc.lua | 23 ++++++++++++++++++++--- rules/regexp/headers.lua | 6 ++++++ rules/regexp/misc.lua | 7 +++++++ 3 files changed, 33 insertions(+), 3 deletions(-) (limited to 'rules') diff --git a/rules/misc.lua b/rules/misc.lua index e289215c9..db754a98e 100644 --- a/rules/misc.lua +++ b/rules/misc.lua @@ -406,7 +406,8 @@ rspamd_config:register_symbol{ score = 0, } -rspamd_config.SPOOF_DISPLAY_NAME = { +local check_from_display_name = rspamd_config:register_symbol{ + name = 'CHECK_FROM_SPOOF', callback = function (task) local from = task:get_from(2) if not (from and from[1] and from[1].name) then return false end @@ -420,16 +421,32 @@ rspamd_config.SPOOF_DISPLAY_NAME = { local to = task:get_recipients(2) -- Be careful with undisclosed-recipients:; as domain will be an empty string if not (to and to[1] and to[1]['domain'] and to[1]['domain'] ~= '') then + task:insert_result('FROM_NEQ_DISPLAY_NAME', 1.0, from[1]['domain'], parsed[1]['domain']) return false end if util.strequal_caseless(to[1]['domain'], parsed[1]['domain']) then - return true,from[1]['domain'],parsed[1]['domain'] + task:insert_result('SPOOF_DISPLAY_NAME', 1.0, from[1]['domain'], parsed[1]['domain']) + return false end end return false end, +} + +rspamd_config:register_symbol{ + type = 'virtual', + parent = check_from_display_name, + name = 'SPOOF_DISPLAY_NAME', description = 'Display name is being used to spoof and trick the recipient', - score = 8.0 + score = 8, +} + +rspamd_config:register_symbol{ + type = 'virtual', + parent = check_from_display_name, + name = 'FROM_NEQ_DISPLAY_NAME', + description = 'Display name contains an email address different to the From address', + score = 4, } rspamd_config.SPOOF_REPLYTO = { diff --git a/rules/regexp/headers.lua b/rules/regexp/headers.lua index f58feeaf8..af63d7131 100644 --- a/rules/regexp/headers.lua +++ b/rules/regexp/headers.lua @@ -899,3 +899,9 @@ reconf['X_PHPOS_FAKE'] = { group = 'headers' } +reconf['HAS_XOIP'] = { + re = "header_exists('X-Originating-IP')", + description = "Has X-Originating-IP header", + score = 0.0, + group = 'headers' +} diff --git a/rules/regexp/misc.lua b/rules/regexp/misc.lua index 2fc194965..5f5b437b6 100644 --- a/rules/regexp/misc.lua +++ b/rules/regexp/misc.lua @@ -40,3 +40,10 @@ reconf['DATA_URI_OBFU'] = { score = 2.0 } +reconf['INTRODUCTION'] = { + re = '/\\b(?:my name is\\b|(?:i am|this is)\\s+(?:mr|mrs|ms|miss|master|sir|prof(?:essor)?|d(?:octo)?r|rev(?:erend)?)(\.|\\b))/{sa_body}i', + description = "Sender introduces themselves", + score = 2.0, + group = 'scams' +} + -- cgit v1.2.3 From 1205d530dd568af6c495c2669e86565219cd7195 Mon Sep 17 00:00:00 2001 From: Steve Freegard Date: Thu, 23 Mar 2017 22:01:19 +0000 Subject: Updates to previous commit --- conf/composites.conf | 6 ++++-- rules/misc.lua | 6 ++++-- rules/regexp/headers.lua | 8 ++++++++ 3 files changed, 16 insertions(+), 4 deletions(-) (limited to 'rules') diff --git a/conf/composites.conf b/conf/composites.conf index 947fa7fbb..8a00b2fd1 100644 --- a/conf/composites.conf +++ b/conf/composites.conf @@ -62,14 +62,16 @@ composites { policy = "leave"; } COMPROMISED_ACCT_BULK { - expression = "HAS_XOIP & DCC_BULK"; - description = "Likely to be from a compromised webmail account"; + expression = "(HAS_XOIP | RCVD_FROM_SMTP_AUTH) & DCC_BULK"; + description = "Likely to be from a compromised account"; score = 3.0; + policy = "leave"; } UNDISC_RCPTS_BULK { expression = "DCC_BULK & (MISSING_TO | R_UNDISC_RCPT)"; description = "Missing or undisclosed recipients with a bulk signature"; score = 3.0; + policy = "leave"; } .include(try=true; priority=1; duplicate=merge) "$LOCAL_CONFDIR/local.d/composites.conf" diff --git a/rules/misc.lua b/rules/misc.lua index db754a98e..1e587d093 100644 --- a/rules/misc.lua +++ b/rules/misc.lua @@ -415,12 +415,14 @@ local check_from_display_name = rspamd_config:register_symbol{ local parsed = util.parse_mail_address(from[1].name) if not parsed then return false end if not (parsed[1] and parsed[1]['addr']) then return false end + if parsed[1]['domain'] == nil or parsed[1]['domain'] == '' then return false end -- See if the parsed domains differ if not util.strequal_caseless(from[1]['domain'], parsed[1]['domain']) then -- See if the destination domain is the same as the spoof local to = task:get_recipients(2) - -- Be careful with undisclosed-recipients:; as domain will be an empty string - if not (to and to[1] and to[1]['domain'] and to[1]['domain'] ~= '') then + if not (to and to[1] and to[1]['domain']) then + -- Be careful with undisclosed-recipients:; as domain will be an empty string + if to[1]['domain'] == nil or to[1]['domain'] == '' then return false end task:insert_result('FROM_NEQ_DISPLAY_NAME', 1.0, from[1]['domain'], parsed[1]['domain']) return false end diff --git a/rules/regexp/headers.lua b/rules/regexp/headers.lua index af63d7131..c14dd3500 100644 --- a/rules/regexp/headers.lua +++ b/rules/regexp/headers.lua @@ -905,3 +905,11 @@ reconf['HAS_XOIP'] = { score = 0.0, group = 'headers' } + +reconf['RCVD_VIA_SMTP_AUTH'] = { + re = "Received=/\\bE?SMTPS?A\\b/ || Received=/\\bauthenticated\\b/i", + description = "Recieved using SMTP AUTH", + score = 0, + group = 'headers' +} + -- cgit v1.2.3 From 1f0efdff27b2d58a04ba51c047785da309012cbf Mon Sep 17 00:00:00 2001 From: Steve Freegard Date: Fri, 24 Mar 2017 10:15:29 +0000 Subject: Rules fixes --- rules/misc.lua | 19 +++++++++++++------ rules/regexp/misc.lua | 2 +- 2 files changed, 14 insertions(+), 7 deletions(-) (limited to 'rules') diff --git a/rules/misc.lua b/rules/misc.lua index 1e587d093..4363d037f 100644 --- a/rules/misc.lua +++ b/rules/misc.lua @@ -456,15 +456,22 @@ rspamd_config.SPOOF_REPLYTO = { -- First check for a Reply-To header local rt = task:get_header('Reply-To') if not rt then return false end - -- Get From header domain - local fromdom = ((task:get_from(2) or E)[1] or E).domain - if not fromdom then return false end + -- Get From and To headers + local from = task:get_from(2) + local to = task:get_recipients(2) + if not (from and from[1] and from[1].addr) then return false end + if (to and to[1] and to[1].addr) then + -- Handle common case for Web Contact forms of From = To + if util.strequal_caseless(from[1].addr, to[1].addr) then + return false + end + end -- SMTP recipients must contain From domain local to = task:get_recipients(1) if not to then return false end local found_fromdom = false for _, t in ipairs(to) do - if util.strequal_caseless(t.domain, fromdom) then + if util.strequal_caseless(t.domain, from[1].domain) then found_fromdom = true break end @@ -474,8 +481,8 @@ rspamd_config.SPOOF_REPLYTO = { local parsed = ((util.parse_mail_address(rt) or E)[1] or E).domain if not parsed then return false end -- Reply-To domain must be different to From domain - if not util.strequal_caseless(parsed, fromdom) then - return true, fromdom, parsed + if not util.strequal_caseless(parsed, from[1].domain) then + return true, from[1].domain, parsed end return false end, diff --git a/rules/regexp/misc.lua b/rules/regexp/misc.lua index 5f5b437b6..2da59ef7f 100644 --- a/rules/regexp/misc.lua +++ b/rules/regexp/misc.lua @@ -41,7 +41,7 @@ reconf['DATA_URI_OBFU'] = { } reconf['INTRODUCTION'] = { - re = '/\\b(?:my name is\\b|(?:i am|this is)\\s+(?:mr|mrs|ms|miss|master|sir|prof(?:essor)?|d(?:octo)?r|rev(?:erend)?)(\.|\\b))/{sa_body}i', + re = '/\\b(?:my name is\\b|(?:i am|this is)\\s+(?:mr|mrs|ms|miss|master|sir|prof(?:essor)?|d(?:octo)?r|rev(?:erend)?)(?:\\.|\\b))/{sa_body}i', description = "Sender introduces themselves", score = 2.0, group = 'scams' -- cgit v1.2.3