git-svn-id: file:///var/lib/svn/clamav-devel/trunk/clamav-devel@1115 77e5149b-7576-45b1-b177-96237e5ba77b
Nigel Horne authored on 2004/11/21 08:05:22... | ... |
@@ -1,3 +1,7 @@ |
1 |
+Sat Nov 20 23:04:59 GMT 2004 (njh) |
|
2 |
+---------------------------------- |
|
3 |
+ * clamav-milter: Better parsing of clamd's reply |
|
4 |
+ |
|
1 | 5 |
Sat Nov 20 13:18:58 GMT 2004 (njh) |
2 | 6 |
---------------------------------- |
3 | 7 |
* libclamav/untar.c: Better handling of false file type identification |
... | ... |
@@ -560,6 +560,12 @@ Changes |
560 | 560 |
localSocket and not quarantine_dir |
561 | 561 |
0.80s 13/11/04 Use SCAN when UNIX socket (localSocket) is used or when the |
562 | 562 |
load balancing algorithm favours localhost |
563 |
+0.80t 20/11/04 Use the improved cli_gentemp(NULL) |
|
564 |
+ Added more samples to ignoredEmailAddresses list, from |
|
565 |
+ "Sergey Y. Afonin" <asy@kraft-s.ru> |
|
566 |
+ Added validation for the reply from clamd |
|
567 |
+ Include the sendmail ID in the quarantine file name, for easier |
|
568 |
+ cross matching with the sendmail log file |
|
563 | 569 |
|
564 | 570 |
INTERNATIONALISATION |
565 | 571 |
|
... | ... |
@@ -26,6 +26,9 @@ |
26 | 26 |
* |
27 | 27 |
* Change History: |
28 | 28 |
* $Log: clamav-milter.c,v $ |
29 |
+ * Revision 1.154 2004/11/20 23:02:23 nigelhorne |
|
30 |
+ * Validate error message from clamd |
|
31 |
+ * |
|
29 | 32 |
* Revision 1.153 2004/11/14 15:18:49 nigelhorne |
30 | 33 |
* Use SCAN in more places rather than STREAM |
31 | 34 |
* |
... | ... |
@@ -470,9 +473,9 @@ |
470 | 470 |
* Revision 1.6 2003/09/28 16:37:23 nigelhorne |
471 | 471 |
* Added -f flag use MaxThreads if --max-children not set |
472 | 472 |
*/ |
473 |
-static char const rcsid[] = "$Id: clamav-milter.c,v 1.153 2004/11/14 15:18:49 nigelhorne Exp $"; |
|
473 |
+static char const rcsid[] = "$Id: clamav-milter.c,v 1.154 2004/11/20 23:02:23 nigelhorne Exp $"; |
|
474 | 474 |
|
475 |
-#define CM_VERSION "0.80s" |
|
475 |
+#define CM_VERSION "0.80t" |
|
476 | 476 |
|
477 | 477 |
/*#define CONFDIR "/usr/local/etc"*/ |
478 | 478 |
|
... | ... |
@@ -679,7 +682,7 @@ static void header_list_print(header_list_t list, FILE *fp); |
679 | 679 |
static int connect2clamd(struct privdata *privdata); |
680 | 680 |
static void checkClamd(void); |
681 | 681 |
static int sendtemplate(SMFICTX *ctx, const char *filename, FILE *sendmail, const char *virusname); |
682 |
-static int qfile(struct privdata *privdata, const char *virusname); |
|
682 |
+static int qfile(struct privdata *privdata, const char *sendmailId, const char *virusname); |
|
683 | 683 |
static void setsubject(SMFICTX *ctx, const char *virusname); |
684 | 684 |
static int clamfi_gethostbyname(const char *hostname, struct hostent *hp, char *buf, size_t len); |
685 | 685 |
static int isLocalAddr(in_addr_t addr); |
... | ... |
@@ -837,7 +840,9 @@ static int quitting; |
837 | 837 |
*/ |
838 | 838 |
static const char *ignoredEmailAddresses[] = { |
839 | 839 |
/*"Mailer-Daemon@bandsman.co.uk", |
840 |
- "postmaster@bandsman.co.uk",*/ |
|
840 |
+ "postmaster@bandsman.co.uk", |
|
841 |
+ "<Mailer-Daemon@bandsman.co.uk>", |
|
842 |
+ "<postmaster@bandsman.co.uk>",*/ |
|
841 | 843 |
NULL |
842 | 844 |
}; |
843 | 845 |
|
... | ... |
@@ -1518,9 +1523,10 @@ main(int argc, char **argv) |
1518 | 1518 |
|
1519 | 1519 |
if((quarantine_dir == NULL) && localSocket) { |
1520 | 1520 |
/* set the temporary dir */ |
1521 |
- if((cpt = cfgopt(copt, "TemporaryDirectory"))) |
|
1521 |
+ if((cpt = cfgopt(copt, "TemporaryDirectory"))) { |
|
1522 | 1522 |
tmpdir = cpt->strarg; |
1523 |
- else if((tmpdir = getenv("TMPDIR")) == (char *)NULL) |
|
1523 |
+ cl_settempdir(tmpdir, (cfgopt(copt, "LeaveTemporaryFiles") != NULL)); |
|
1524 |
+ } else if((tmpdir = getenv("TMPDIR")) == (char *)NULL) |
|
1524 | 1525 |
if((tmpdir = getenv("TMP")) == (char *)NULL) |
1525 | 1526 |
if((tmpdir = getenv("TEMP")) == (char *)NULL) |
1526 | 1527 |
#ifdef P_tmpdir |
... | ... |
@@ -1529,13 +1535,12 @@ main(int argc, char **argv) |
1529 | 1529 |
tmpdir = "/tmp"; |
1530 | 1530 |
#endif |
1531 | 1531 |
|
1532 |
- tmpdir = cli_gentemp(tmpdir); |
|
1532 |
+ tmpdir = cli_gentemp(NULL); |
|
1533 | 1533 |
|
1534 | 1534 |
if(mkdir(tmpdir, 0700)) { |
1535 | 1535 |
perror(tmpdir); |
1536 | 1536 |
return EX_CANTCREAT; |
1537 | 1537 |
} |
1538 |
- cl_settempdir(tmpdir, (cfgopt(copt, "LeaveTemporaryFiles") != NULL)); |
|
1539 | 1538 |
} else |
1540 | 1539 |
tmpdir = NULL; |
1541 | 1540 |
|
... | ... |
@@ -2439,7 +2444,7 @@ clamfi_eoh(SMFICTX *ctx) |
2439 | 2439 |
if(use_syslog) |
2440 | 2440 |
syslog(LOG_NOTICE, _("clamfi_eoh: ignoring whitelisted message")); |
2441 | 2441 |
#ifdef CL_DEBUG |
2442 |
- cli_dbgmsg(_("clamfi_eoh: not scanning outgoing messages\n")); |
|
2442 |
+ cli_dbgmsg(_("clamfi_eoh: ignoring whitelisted message\n")); |
|
2443 | 2443 |
#endif |
2444 | 2444 |
clamfi_cleanup(ctx); |
2445 | 2445 |
|
... | ... |
@@ -2707,33 +2712,7 @@ clamfi_eom(SMFICTX *ctx) |
2707 | 2707 |
if(use_syslog) |
2708 | 2708 |
syslog(LOG_ERR, "%s: %s\n", sendmailId, mess); |
2709 | 2709 |
rc = cl_error; |
2710 |
- } else if((ptr = strstr(mess, "FOUND")) == NULL) { |
|
2711 |
- if(!nflag) |
|
2712 |
- smfi_addheader(ctx, "X-Virus-Status", _("Clean")); |
|
2713 |
- |
|
2714 |
- if(use_syslog && logClean) |
|
2715 |
- /* Include the sendmail queue ID in the log */ |
|
2716 |
- syslog(LOG_NOTICE, _("%s: clean message from %s"), |
|
2717 |
- sendmailId, |
|
2718 |
- (privdata->from) ? privdata->from : _("an unknown sender")); |
|
2719 |
- |
|
2720 |
- if(privdata->body) { |
|
2721 |
- /* |
|
2722 |
- * Add a signature that all has been scanned OK |
|
2723 |
- */ |
|
2724 |
- off_t len = updateSigFile(); |
|
2725 |
- |
|
2726 |
- if(len) { |
|
2727 |
- assert(Sflag != 0); |
|
2728 |
- |
|
2729 |
- privdata->body = cli_realloc(privdata->body, privdata->bodyLen + len); |
|
2730 |
- if(privdata->body) { |
|
2731 |
- memcpy(&privdata->body[privdata->bodyLen], signature, len); |
|
2732 |
- smfi_replacebody(ctx, privdata->body, privdata->bodyLen + len); |
|
2733 |
- } |
|
2734 |
- } |
|
2735 |
- } |
|
2736 |
- } else { |
|
2710 |
+ } else if((ptr = strstr(mess, "FOUND")) != NULL) { |
|
2737 | 2711 |
char reject[1024]; |
2738 | 2712 |
char **to, *virusname; |
2739 | 2713 |
|
... | ... |
@@ -2901,7 +2880,7 @@ clamfi_eom(SMFICTX *ctx) |
2901 | 2901 |
fprintf(sendmail, _("contained %s and has not been delivered.\n"), virusname); |
2902 | 2902 |
|
2903 | 2903 |
if(quarantine_dir != NULL) |
2904 |
- if(qfile(privdata, virusname) == 0) |
|
2904 |
+ if(qfile(privdata, sendmailId, virusname) == 0) |
|
2905 | 2905 |
fprintf(sendmail, _("\nThe message in question has been quarantined as %s\n"), privdata->filename); |
2906 | 2906 |
|
2907 | 2907 |
if(hflag) { |
... | ... |
@@ -2974,6 +2953,40 @@ clamfi_eom(SMFICTX *ctx) |
2974 | 2974 |
snprintf(reject, sizeof(reject) - 1, _("virus %s detected by ClamAV - http://www.clamav.net"), virusname); |
2975 | 2975 |
smfi_setreply(ctx, (char *)privdata->rejectCode, "5.7.1", reject); |
2976 | 2976 |
broadcast(mess); |
2977 |
+ } else if((ptr = strstr(mess, "OK")) == NULL) { |
|
2978 |
+ if(!nflag) |
|
2979 |
+ smfi_addheader(ctx, "X-Virus-Status", _("Unknown")); |
|
2980 |
+ if(use_syslog) |
|
2981 |
+ syslog(LOG_ERR, _("%s: incorrect message \"%s\" from clamd"), |
|
2982 |
+ sendmailId, |
|
2983 |
+ mess); |
|
2984 |
+ rc = cl_error; |
|
2985 |
+ } else { |
|
2986 |
+ if(!nflag) |
|
2987 |
+ smfi_addheader(ctx, "X-Virus-Status", _("Clean")); |
|
2988 |
+ |
|
2989 |
+ if(use_syslog && logClean) |
|
2990 |
+ /* Include the sendmail queue ID in the log */ |
|
2991 |
+ syslog(LOG_NOTICE, _("%s: clean message from %s"), |
|
2992 |
+ sendmailId, |
|
2993 |
+ (privdata->from) ? privdata->from : _("an unknown sender")); |
|
2994 |
+ |
|
2995 |
+ if(privdata->body) { |
|
2996 |
+ /* |
|
2997 |
+ * Add a signature that all has been scanned OK |
|
2998 |
+ */ |
|
2999 |
+ off_t len = updateSigFile(); |
|
3000 |
+ |
|
3001 |
+ if(len) { |
|
3002 |
+ assert(Sflag != 0); |
|
3003 |
+ |
|
3004 |
+ privdata->body = cli_realloc(privdata->body, privdata->bodyLen + len); |
|
3005 |
+ if(privdata->body) { |
|
3006 |
+ memcpy(&privdata->body[privdata->bodyLen], signature, len); |
|
3007 |
+ smfi_replacebody(ctx, privdata->body, privdata->bodyLen + len); |
|
3008 |
+ } |
|
3009 |
+ } |
|
3010 |
+ } |
|
2977 | 3011 |
} |
2978 | 3012 |
clamfi_cleanup(ctx); |
2979 | 3013 |
|
... | ... |
@@ -3455,11 +3468,7 @@ connect2clamd(struct privdata *privdata) |
3455 | 3455 |
cli_dbgmsg("connect2clamd\n"); |
3456 | 3456 |
#endif |
3457 | 3457 |
|
3458 |
- if(quarantine_dir || tmpdir) { |
|
3459 |
- /* |
|
3460 |
- * quarantine_dir is specified |
|
3461 |
- * store message in a temporary file |
|
3462 |
- */ |
|
3458 |
+ if(quarantine_dir || tmpdir) { /* store message in a temporary file */ |
|
3463 | 3459 |
int ntries = 5; |
3464 | 3460 |
time_t t; |
3465 | 3461 |
int MM, YY, DD; |
... | ... |
@@ -3512,7 +3521,8 @@ connect2clamd(struct privdata *privdata) |
3512 | 3512 |
return 0; |
3513 | 3513 |
} |
3514 | 3514 |
privdata->serverNumber = 0; |
3515 |
- } else { |
|
3515 |
+ cli_dbgmsg("Saving message to %s to scan later\n", privdata->filename); |
|
3516 |
+ } else { /* communicate to clamd */ |
|
3516 | 3517 |
int freeServer, nbytes; |
3517 | 3518 |
struct sockaddr_in reply; |
3518 | 3519 |
unsigned short p; |
... | ... |
@@ -3546,7 +3556,7 @@ connect2clamd(struct privdata *privdata) |
3546 | 3546 |
privdata->serverNumber = 0; |
3547 | 3547 |
#endif |
3548 | 3548 |
freeServer = 0; |
3549 |
- } else { |
|
3549 |
+ } else { /* TCP/IP */ |
|
3550 | 3550 |
#ifdef SESSION |
3551 | 3551 |
freeServer = findServer(); |
3552 | 3552 |
if(freeServer < 0) |
... | ... |
@@ -3580,18 +3590,7 @@ connect2clamd(struct privdata *privdata) |
3580 | 3580 |
|
3581 | 3581 |
#ifdef SESSION |
3582 | 3582 |
if(serverIPs[freeServer] == inet_addr("127.0.0.1")) { |
3583 |
- const char *dir; |
|
3584 |
- |
|
3585 |
- if((dir = getenv("TMPDIR")) == (char *)NULL) |
|
3586 |
- if((dir = getenv("TMP")) == (char *)NULL) |
|
3587 |
- if((dir = getenv("TEMP")) == (char *)NULL) |
|
3588 |
-#ifdef P_tmpdir |
|
3589 |
- dir = P_tmpdir; |
|
3590 |
-#else |
|
3591 |
- dir = "/tmp"; |
|
3592 |
-#endif |
|
3593 |
- |
|
3594 |
- privdata->filename = cli_gentemp(dir); |
|
3583 |
+ privdata->filename = cli_gentemp(NULL); |
|
3595 | 3584 |
if(privdata->filename) { |
3596 | 3585 |
cli_dbgmsg("connect2clamd(%d): creating %s\n", freeServer, privdata->filename); |
3597 | 3586 |
#ifdef O_TEXT |
... | ... |
@@ -3721,7 +3720,6 @@ connect2clamd(struct privdata *privdata) |
3721 | 3721 |
} |
3722 | 3722 |
|
3723 | 3723 |
end: |
3724 |
- |
|
3725 | 3724 |
/* |
3726 | 3725 |
* Combine the To and From into one clamfi_send to save bandwidth |
3727 | 3726 |
* when sending using TCP/IP to connect to a remote clamd, by band |
... | ... |
@@ -3915,7 +3913,7 @@ sendtemplate(SMFICTX *ctx, const char *filename, FILE *sendmail, const char *vir |
3915 | 3915 |
* Keep the infected file in quarantine, return success (0) or failure |
3916 | 3916 |
*/ |
3917 | 3917 |
static int |
3918 |
-qfile(struct privdata *privdata, const char *virusname) |
|
3918 |
+qfile(struct privdata *privdata, const char *sendmailId, const char *virusname) |
|
3919 | 3919 |
{ |
3920 | 3920 |
char *newname, *ptr; |
3921 | 3921 |
size_t len; |
... | ... |
@@ -3927,12 +3925,12 @@ qfile(struct privdata *privdata, const char *virusname) |
3927 | 3927 |
|
3928 | 3928 |
len = strlen(privdata->filename); |
3929 | 3929 |
|
3930 |
- newname = cli_malloc(len + strlen(virusname) + 2); |
|
3930 |
+ newname = cli_malloc(len + strlen(sendmailId) + strlen(virusname) + 3); |
|
3931 | 3931 |
|
3932 | 3932 |
if(newname == NULL) |
3933 | 3933 |
return -1; |
3934 | 3934 |
|
3935 |
- sprintf(newname, "%s.%s", privdata->filename, virusname); |
|
3935 |
+ sprintf(newname, "%s.%s.%s", privdata->filename, sendmailId, virusname); |
|
3936 | 3936 |
|
3937 | 3937 |
/* |
3938 | 3938 |
* Strip out funnies that may be in the name of the virus, such as '/' |
... | ... |
@@ -4184,9 +4182,12 @@ watchdog(void *a) |
4184 | 4184 |
if(strncmp(buf, "ClamAV ", 7) == 0) { |
4185 | 4185 |
/* Remove the trailing new line from the reply */ |
4186 | 4186 |
char *ptr; |
4187 |
+ |
|
4187 | 4188 |
if((ptr = strchr(buf, '\n')) != NULL) |
4188 | 4189 |
*ptr = '\0'; |
4189 |
- if(strcmp(buf, clamav_versions[i]) != 0) { |
|
4190 |
+ if(clamav_versions[i] == NULL) |
|
4191 |
+ clamav_versions[i] = strdup(buf); |
|
4192 |
+ else if(strcmp(buf, clamav_versions[i]) != 0) { |
|
4190 | 4193 |
if(use_syslog) |
4191 | 4194 |
syslog(LOG_INFO, "New version received for server %d: '%s'\n", i, buf); |
4192 | 4195 |
free(clamav_versions[i]); |