git-svn-id: file:///var/lib/svn/clamav-devel/trunk/clamav-devel@540 77e5149b-7576-45b1-b177-96237e5ba77b
Nigel Horne authored on 2004/05/06 20:25:20... | ... |
@@ -374,6 +374,12 @@ Changes |
374 | 374 |
been given. There has never been one to return |
375 | 375 |
0.70u 29/4/04 When changing from realloc to cli_realloc I forgot to keep the |
376 | 376 |
assignment of signature |
377 |
+0.70v 6/5/04 clamfi_close now always checks privdata is NULL, not only when |
|
378 |
+ debugging |
|
379 |
+ Allow transfers of exactly streamMaxLength |
|
380 |
+ Warn if a clean file can't be removed from the quarantine |
|
381 |
+ When streamMaxLength is exceeded add a header where possible, |
|
382 |
+ unless --noxheader is given |
|
377 | 383 |
|
378 | 384 |
BUG REPORTS |
379 | 385 |
|
... | ... |
@@ -376,9 +376,19 @@ |
376 | 376 |
* one to return |
377 | 377 |
* 0.70u 29/4/04 When changing from realloc to cli_realloc I forgot |
378 | 378 |
* to keep the assignment of signature |
379 |
+ * 0.70v 6/5/04 clamfi_close now always checks privdata is NULL, not |
|
380 |
+ * only when debugging |
|
381 |
+ * Allow transfers of exactly streamMaxLength |
|
382 |
+ * Warn if a clean file can't be removed from the |
|
383 |
+ * quarantine |
|
384 |
+ * When streamMaxLength is exceeded add a header where |
|
385 |
+ * possible, unless --noxheader is given |
|
379 | 386 |
* |
380 | 387 |
* Change History: |
381 | 388 |
* $Log: clamav-milter.c,v $ |
389 |
+ * Revision 1.86 2004/05/06 11:25:20 nigelhorne |
|
390 |
+ * Some work on maxStreamLength |
|
391 |
+ * |
|
382 | 392 |
* Revision 1.85 2004/04/29 07:35:27 nigelhorne |
383 | 393 |
* Change from realloc to cli_realloc - keep assignment |
384 | 394 |
* |
... | ... |
@@ -619,9 +629,9 @@ |
619 | 619 |
* Revision 1.6 2003/09/28 16:37:23 nigelhorne |
620 | 620 |
* Added -f flag use MaxThreads if --max-children not set |
621 | 621 |
*/ |
622 |
-static char const rcsid[] = "$Id: clamav-milter.c,v 1.85 2004/04/29 07:35:27 nigelhorne Exp $"; |
|
622 |
+static char const rcsid[] = "$Id: clamav-milter.c,v 1.86 2004/05/06 11:25:20 nigelhorne Exp $"; |
|
623 | 623 |
|
624 |
-#define CM_VERSION "0.70u" |
|
624 |
+#define CM_VERSION "0.70v" |
|
625 | 625 |
|
626 | 626 |
/*#define CONFDIR "/usr/local/etc"*/ |
627 | 627 |
|
... | ... |
@@ -755,7 +765,7 @@ static sfsistat clamfi_abort(SMFICTX *ctx); |
755 | 755 |
static sfsistat clamfi_close(SMFICTX *ctx); |
756 | 756 |
static void clamfi_cleanup(SMFICTX *ctx); |
757 | 757 |
static void clamfi_free(struct privdata *privdata); |
758 |
-static int clamfi_send(const struct privdata *privdata, size_t len, const char *format, ...); |
|
758 |
+static int clamfi_send(struct privdata *privdata, size_t len, const char *format, ...); |
|
759 | 759 |
static char *strrcpy(char *dest, const char *source); |
760 | 760 |
static int clamd_recv(int sock, char *buf, size_t len); |
761 | 761 |
static off_t updateSigFile(void); |
... | ... |
@@ -857,8 +867,10 @@ static const char *postmaster = "postmaster"; |
857 | 857 |
static const char *from = "MAILER-DAEMON"; |
858 | 858 |
|
859 | 859 |
/* |
860 |
- * Whitelist of source e-mail addresses that we do NOT scan |
|
860 |
+ * NULL terminated whitelist of source e-mail addresses that we do NOT scan |
|
861 | 861 |
* TODO: read in from a file |
862 |
+ * TODO: add white list of target e-mail addresses that we do NOT scan |
|
863 |
+ * TODO: items in the list should be regular expressions |
|
862 | 864 |
*/ |
863 | 865 |
static const char *ignoredEmailAddresses[] = { |
864 | 866 |
/*"Mailer-Daemon@bandsman.co.uk", |
... | ... |
@@ -1895,9 +1907,6 @@ clamfi_envfrom(SMFICTX *ctx, char **argv) |
1895 | 1895 |
|
1896 | 1896 |
privdata->from = strdup(argv[0]); |
1897 | 1897 |
|
1898 |
- if(streamMaxLength > 0L) |
|
1899 |
- privdata->numBytes = (long)(strlen(argv[0]) + 6); |
|
1900 |
- |
|
1901 | 1898 |
if(hflag) |
1902 | 1899 |
privdata->headers = header_list_new(); |
1903 | 1900 |
|
... | ... |
@@ -1932,9 +1941,6 @@ clamfi_envrcpt(SMFICTX *ctx, char **argv) |
1932 | 1932 |
privdata->to[privdata->numTo] = strdup(argv[0]); |
1933 | 1933 |
privdata->to[++privdata->numTo] = NULL; |
1934 | 1934 |
|
1935 |
- if(streamMaxLength > 0L) |
|
1936 |
- privdata->numBytes += (long)(strlen(argv[0]) + 4); |
|
1937 |
- |
|
1938 | 1935 |
return SMFIS_CONTINUE; |
1939 | 1936 |
} |
1940 | 1937 |
|
... | ... |
@@ -1966,14 +1972,11 @@ clamfi_header(SMFICTX *ctx, char *headerf, char *headerv) |
1966 | 1966 |
return cl_error; |
1967 | 1967 |
} |
1968 | 1968 |
|
1969 |
- if(clamfi_send(privdata, 0, "%s: %s\n", headerf, headerv) < 0) { |
|
1969 |
+ if(clamfi_send(privdata, 0, "%s: %s\n", headerf, headerv) <= 0) { |
|
1970 | 1970 |
clamfi_cleanup(ctx); |
1971 | 1971 |
return cl_error; |
1972 | 1972 |
} |
1973 | 1973 |
|
1974 |
- if(streamMaxLength > 0L) |
|
1975 |
- privdata->numBytes += (long)(strlen(headerf) + strlen(headerv) + 3); |
|
1976 |
- |
|
1977 | 1974 |
if(hflag) |
1978 | 1975 |
header_list_add(privdata->headers, headerf, headerv); |
1979 | 1976 |
else if((strcasecmp(headerf, "Received") == 0) && |
... | ... |
@@ -2021,12 +2024,10 @@ clamfi_eoh(SMFICTX *ctx) |
2021 | 2021 |
return cl_error; |
2022 | 2022 |
} |
2023 | 2023 |
|
2024 |
- if(clamfi_send(privdata, 1, "\n") < 0) { |
|
2024 |
+ if(clamfi_send(privdata, 1, "\n") != 1) { |
|
2025 | 2025 |
clamfi_cleanup(ctx); |
2026 | 2026 |
return cl_error; |
2027 | 2027 |
} |
2028 |
- if(streamMaxLength > 0L) |
|
2029 |
- privdata->numBytes++; |
|
2030 | 2028 |
|
2031 | 2029 |
/* |
2032 | 2030 |
* See if the e-mail is only going to members of the list |
... | ... |
@@ -2076,6 +2077,7 @@ static sfsistat |
2076 | 2076 |
clamfi_body(SMFICTX *ctx, u_char *bodyp, size_t len) |
2077 | 2077 |
{ |
2078 | 2078 |
struct privdata *privdata = (struct privdata *)smfi_getpriv(ctx); |
2079 |
+ int nbytes; |
|
2079 | 2080 |
|
2080 | 2081 |
if(logVerbose) |
2081 | 2082 |
syslog(LOG_DEBUG, "clamfi_envbody: %u bytes", len); |
... | ... |
@@ -2083,8 +2085,8 @@ clamfi_body(SMFICTX *ctx, u_char *bodyp, size_t len) |
2083 | 2083 |
cli_dbgmsg("clamfi_envbody: %u bytes\n", len); |
2084 | 2084 |
#endif |
2085 | 2085 |
|
2086 |
+ nbytes = clamfi_send(privdata, len, (char *)bodyp); |
|
2086 | 2087 |
if(streamMaxLength > 0L) { |
2087 |
- privdata->numBytes += (long)len; |
|
2088 | 2088 |
if(privdata->numBytes > streamMaxLength) { |
2089 | 2089 |
if(use_syslog) { |
2090 | 2090 |
const char *sendmailId = smfi_getsymval(ctx, "i"); |
... | ... |
@@ -2093,11 +2095,13 @@ clamfi_body(SMFICTX *ctx, u_char *bodyp, size_t len) |
2093 | 2093 |
syslog(LOG_NOTICE, "%s: Message more than StreamMaxLength (%ld) bytes - not scanned", |
2094 | 2094 |
sendmailId, streamMaxLength); |
2095 | 2095 |
} |
2096 |
- clamfi_cleanup(ctx); /* not needed, but just to be safe */ |
|
2097 |
- return SMFIS_ACCEPT; |
|
2096 |
+ if(!nflag) |
|
2097 |
+ smfi_addheader(ctx, "X-Virus-Status", "Not Scanned - StreamMaxLength exceeded"); |
|
2098 |
+ |
|
2099 |
+ return SMFIS_ACCEPT; /* clamfi_close will be called */ |
|
2098 | 2100 |
} |
2099 | 2101 |
} |
2100 |
- if(clamfi_send(privdata, len, (char *)bodyp) < 0) { |
|
2102 |
+ if(nbytes < len) { |
|
2101 | 2103 |
clamfi_cleanup(ctx); /* not needed, but just to be safe */ |
2102 | 2104 |
return cl_error; |
2103 | 2105 |
} |
... | ... |
@@ -2206,9 +2210,6 @@ clamfi_eom(SMFICTX *ctx) |
2206 | 2206 |
smfi_addheader(ctx, "X-Virus-Scanned", clamav_version); |
2207 | 2207 |
|
2208 | 2208 |
if(strstr(mess, "ERROR") != NULL) { |
2209 |
- if(!nflag) |
|
2210 |
- smfi_addheader(ctx, "X-Virus-Status", "Not Scanned"); |
|
2211 |
- |
|
2212 | 2209 |
if(strstr(mess, "Size exceeded") != NULL) { |
2213 | 2210 |
/* |
2214 | 2211 |
* Clamd has stopped on StreamMaxLength before us |
... | ... |
@@ -2217,8 +2218,12 @@ clamfi_eom(SMFICTX *ctx) |
2217 | 2217 |
syslog(LOG_NOTICE, "%s: Message more than StreamMaxLength (%ld) bytes - not scanned", |
2218 | 2218 |
sendmailId, streamMaxLength); |
2219 | 2219 |
clamfi_cleanup(ctx); /* not needed, but just to be safe */ |
2220 |
+ if(!nflag) |
|
2221 |
+ smfi_addheader(ctx, "X-Virus-Status", "Not Scanned - StreamMaxLength exceeded"); |
|
2220 | 2222 |
return SMFIS_ACCEPT; |
2221 | 2223 |
} |
2224 |
+ if(!nflag) |
|
2225 |
+ smfi_addheader(ctx, "X-Virus-Status", "Not Scanned"); |
|
2222 | 2226 |
|
2223 | 2227 |
cli_warnmsg("%s: %s\n", sendmailId, mess); |
2224 | 2228 |
if(use_syslog) |
... | ... |
@@ -2430,7 +2435,9 @@ clamfi_eom(SMFICTX *ctx) |
2430 | 2430 |
if(use_syslog) |
2431 | 2431 |
syslog(LOG_NOTICE, "Quarantined infected mail as %s", privdata->filename); |
2432 | 2432 |
/* |
2433 |
- * Cleanup filename here! Default procedure would delete quarantine file |
|
2433 |
+ * Cleanup filename here otherwise clamfi_free() will |
|
2434 |
+ * delete the file that we wish to keep because it |
|
2435 |
+ * is infected |
|
2434 | 2436 |
*/ |
2435 | 2437 |
free(privdata->filename); |
2436 | 2438 |
privdata->filename = NULL; |
... | ... |
@@ -2504,17 +2511,11 @@ clamfi_abort(SMFICTX *ctx) |
2504 | 2504 |
static sfsistat |
2505 | 2505 |
clamfi_close(SMFICTX *ctx) |
2506 | 2506 |
{ |
2507 |
-#ifdef CL_DEBUG |
|
2508 | 2507 |
struct privdata *privdata = (struct privdata *)smfi_getpriv(ctx); |
2509 | 2508 |
|
2510 | 2509 |
cli_dbgmsg("clamfi_close\n"); |
2511 |
- if(privdata != NULL) { |
|
2512 |
- if(use_syslog) |
|
2513 |
- syslog(LOG_DEBUG, "clamfi_close, privdata != NULL"); |
|
2514 |
- else |
|
2515 |
- cli_warnmsg("clamfi_close, privdata != NULL"); |
|
2516 |
- } |
|
2517 |
-#endif |
|
2510 |
+ if(privdata != NULL) |
|
2511 |
+ clamfi_cleanup(ctx); |
|
2518 | 2512 |
|
2519 | 2513 |
if(logVerbose) |
2520 | 2514 |
syslog(LOG_DEBUG, "clamfi_close"); |
... | ... |
@@ -2546,8 +2547,13 @@ clamfi_free(struct privdata *privdata) |
2546 | 2546 |
} |
2547 | 2547 |
|
2548 | 2548 |
if(privdata->filename != NULL) { |
2549 |
- if(unlink(privdata->filename) < 0) |
|
2549 |
+ if(unlink(privdata->filename) < 0) { |
|
2550 | 2550 |
perror(privdata->filename); |
2551 |
+ if(use_syslog) |
|
2552 |
+ syslog(LOG_ERR, |
|
2553 |
+ "Can't remove clean file %s", |
|
2554 |
+ privdata->filename); |
|
2555 |
+ } |
|
2551 | 2556 |
free(privdata->filename); |
2552 | 2557 |
privdata->filename = NULL; |
2553 | 2558 |
} |
... | ... |
@@ -2621,13 +2627,14 @@ clamfi_free(struct privdata *privdata) |
2621 | 2621 |
} |
2622 | 2622 |
|
2623 | 2623 |
/* |
2624 |
- * Returns < 0 for failure |
|
2624 |
+ * Returns < 0 for failure, otherwise the number of bytes sent |
|
2625 | 2625 |
*/ |
2626 | 2626 |
static int |
2627 |
-clamfi_send(const struct privdata *privdata, size_t len, const char *format, ...) |
|
2627 |
+clamfi_send(struct privdata *privdata, size_t len, const char *format, ...) |
|
2628 | 2628 |
{ |
2629 | 2629 |
char output[BUFSIZ]; |
2630 | 2630 |
const char *ptr; |
2631 |
+ int ret = 0; |
|
2631 | 2632 |
|
2632 | 2633 |
assert(format != NULL); |
2633 | 2634 |
|
... | ... |
@@ -2687,10 +2694,17 @@ clamfi_send(const struct privdata *privdata, size_t len, const char *format, ... |
2687 | 2687 |
|
2688 | 2688 |
return -1; |
2689 | 2689 |
} |
2690 |
+ ret += nbytes; |
|
2690 | 2691 |
len -= nbytes; |
2691 | 2692 |
ptr = &ptr[nbytes]; |
2693 |
+ |
|
2694 |
+ if(streamMaxLength > 0L) { |
|
2695 |
+ privdata->numBytes += nbytes; |
|
2696 |
+ if(privdata->numBytes >= streamMaxLength) |
|
2697 |
+ break; |
|
2698 |
+ } |
|
2692 | 2699 |
} |
2693 |
- return 0; |
|
2700 |
+ return ret; |
|
2694 | 2701 |
} |
2695 | 2702 |
|
2696 | 2703 |
/* |
... | ... |
@@ -3057,7 +3071,7 @@ connect2clamd(struct privdata *privdata) |
3057 | 3057 |
privdata->from); |
3058 | 3058 |
|
3059 | 3059 |
for(to = privdata->to; *to; to++) |
3060 |
- if(clamfi_send(privdata, 0, "To: %s\n", *to) < 0) |
|
3060 |
+ if(clamfi_send(privdata, 0, "To: %s\n", *to) <= 0) |
|
3061 | 3061 |
return 0; |
3062 | 3062 |
|
3063 | 3063 |
cli_dbgmsg("connect2clamd OK\n"); |