diff options
Diffstat (limited to 'src/clamsmtpd.c')
-rw-r--r-- | src/clamsmtpd.c | 77 |
1 files changed, 67 insertions, 10 deletions
diff --git a/src/clamsmtpd.c b/src/clamsmtpd.c index 93d773f..52921dc 100644 --- a/src/clamsmtpd.c +++ b/src/clamsmtpd.c @@ -58,6 +58,12 @@ * STRUCTURES */ +enum { + ACTION_DROP, + ACTION_BOUNCE, + ACTION_PASS +}; + typedef struct clstate { /* Settings ------------------------------- */ @@ -65,9 +71,10 @@ typedef struct clstate const char* clamname; const char* directory; /* The directory for temp files */ const char* virusaction; /* Program to run when event occurs */ - int bounce; /* Send back a reject line */ + int action; /* Which action to take on a virus */ int quarantine; /* Leave virus files in temp dir */ int debug_files; /* Leave all files in temp dir */ + const char* header; /* A header to include in emails */ } clstate_t; @@ -102,6 +109,7 @@ clctx_t; #define DEFAULT_CONFIG CONF_PREFIX "/clamsmtpd.conf" #define DEFAULT_CLAMAV "/var/run/clamav/clamd" #define DEFAULT_HEADER "X-Virus-Scanned: ClamAV using ClamSMTP" +#define VIRUS_HEADER "X-Virus-Infected: Virus Detected!" /* ----------------------------------------------------------------------- * CONFIGURATION OPTIONS @@ -122,11 +130,17 @@ clctx_t; #define CFG_DIRECTORY "TempDirectory" #define CFG_HEADER "Header" #define CFG_SCANHEADER "ScanHeader" +#define CFG_HEADER "Header" #define CFG_BOUNCE "Bounce" +#define CFG_ACTION "Action" #define CFG_QUARANTINE "Quarantine" #define CFG_DEBUGFILES "DebugFiles" #define CFG_VIRUSACTION "VirusAction" +#define VAL_BOUNCE "bounce" +#define VAL_DROP "drop" +#define VAL_PASS "pass" + /* ----------------------------------------------------------------------- * GLOBALS */ @@ -208,7 +222,7 @@ int main(int argc, char* argv[]) warnargs = 1; break; - /* Don't daemonize */ + /* Don't daemonize */ case 'd': dbg_level = strtol(optarg, &t, 10); if(*t) /* parse error */ @@ -366,7 +380,7 @@ int cb_check_data(spctx_t* sp) * and transfer the file to it. */ case 0: - if(sp_done_data(sp) == -1) + if(sp_done_data(sp, g_clstate.header) == -1) return -1; break; @@ -380,9 +394,25 @@ int cb_check_data(spctx_t* sp) /* Any special post operation actions on the virus */ virus_action(ctx, virus); - if(sp_fail_data(sp, g_clstate.bounce ? - SMTP_DATAVIRUS : SMTP_DATAVIRUSOK) == -1) - return -1; + switch(g_clstate.action) + { + case ACTION_DROP: + if(sp_fail_data(sp, SMTP_DATAVIRUSOK) == -1) + return -1; + break; + case ACTION_BOUNCE: + if(sp_fail_data(sp, SMTP_DATAVIRUS) == -1) + return -1; + break; + case ACTION_PASS: + if(sp_done_data(sp, VIRUS_HEADER) == -1) + return -1; + break; + default: + ASSERT(0 && "Invalid action"); + break; + } + break; default: @@ -403,11 +433,21 @@ int cb_parse_option(const char* name, const char* value) return 1; } - /* COMPAT: Parse old header option */ + /* COMPAT: Parse old header option */ else if(strcasecmp(CFG_SCANHEADER, name) == 0) { warnx("please use \"Header\" option instead of \"ScanHeader\""); - return sp_parse_option(CFG_HEADER, value); + g_clstate.header = trim_start(value); + if(strlen(g_clstate.header) == 0) + g_clstate.header = NULL; + } + + else if(strcasecmp(CFG_HEADER, name) == 0) + { + g_clstate.header = trim_start(value); + if(strlen(g_clstate.header) == 0) + g_clstate.header = NULL; + return 1; } else if(strcasecmp(CFG_DIRECTORY, name) == 0) @@ -416,17 +456,34 @@ int cb_parse_option(const char* name, const char* value) return 1; } + /* COMPAT: Subsumed by the 'Action' option */ else if(strcasecmp(CFG_BOUNCE, name) == 0) { - if((g_clstate.bounce = strtob(value)) == -1) + int bounce = strtob(value); + if(bounce == -1) errx(2, "invalid value for " CFG_BOUNCE); + if(bounce) + g_clstate.action = ACTION_BOUNCE; + warnx("please use \"Action\" option instead of \"Bounce\""); return 1; } + else if(strcasecmp(CFG_ACTION, name) == 0) + { + if(strcasecmp(VAL_BOUNCE, value) == 0) + g_clstate.action = ACTION_BOUNCE; + else if(strcasecmp(VAL_DROP, value) == 0) + g_clstate.action = ACTION_DROP; + else if(strcasecmp(VAL_PASS, value) == 0) + g_clstate.action = ACTION_PASS; + else + errx(2, "invalid value for " CFG_ACTION); + } + else if(strcasecmp(CFG_QUARANTINE, name) == 0) { if((g_clstate.quarantine = strtob(value)) == -1) - errx(2, "invalid value for " CFG_BOUNCE); + errx(2, "invalid value for " CFG_QUARANTINE); return 1; } |