Browse code

Added dont-wait and advisory options

git-svn-id: file:///var/lib/svn/clamav-devel/trunk/clamav-devel@669 77e5149b-7576-45b1-b177-96237e5ba77b

Nigel Horne authored on 2004/07/14 19:18:36
Showing 4 changed files
... ...
@@ -1,3 +1,7 @@
1
+Wed Jul 14 11:17:58 BST 2004 (njh)
2
+----------------------------------
3
+  * clamav-milter:	Added --dont-wait and --advisory options
4
+
1 5
 Tue Jul 13 18:37:23 CEST 2004 (tk)
2 6
 ----------------------------------
3 7
   * libclamav: upx: fix potential infinite loop (aCaB)
... ...
@@ -421,6 +421,8 @@ Changes
421 421
 0.74	29/6/04	Up-issued
422 422
 0.74a	29/6/04	Allow the child timeout to be configurable
423 423
 0.74b	8/7/04	Validate the arguments to inet_ntop
424
+0.74c	14/7/04	Added --dont-wait
425
+		Added --advisory
424 426
 
425 427
 BUG REPORTS
426 428
 
... ...
@@ -26,6 +26,9 @@
26 26
  *
27 27
  * Change History:
28 28
  * $Log: clamav-milter.c,v $
29
+ * Revision 1.104  2004/07/14 10:17:05  nigelhorne
30
+ * Added dont-wait and advisory options
31
+ *
29 32
  * Revision 1.103  2004/07/08 22:22:39  nigelhorne
30 33
  * Don't pass empty arguments to inet_ntop
31 34
  *
... ...
@@ -320,9 +323,9 @@
320 320
  * Revision 1.6  2003/09/28 16:37:23  nigelhorne
321 321
  * Added -f flag use MaxThreads if --max-children not set
322 322
  */
323
-static	char	const	rcsid[] = "$Id: clamav-milter.c,v 1.103 2004/07/08 22:22:39 nigelhorne Exp $";
323
+static	char	const	rcsid[] = "$Id: clamav-milter.c,v 1.104 2004/07/14 10:17:05 nigelhorne Exp $";
324 324
 
325
-#define	CM_VERSION	"0.74b"
325
+#define	CM_VERSION	"0.74c"
326 326
 
327 327
 /*#define	CONFDIR	"/usr/local/etc"*/
328 328
 
... ...
@@ -469,6 +472,7 @@ static	void	header_list_print(header_list_t list, FILE *fp);
469 469
 static	int	connect2clamd(struct privdata *privdata);
470 470
 static	void	checkClamd(void);
471 471
 static	int	sendtemplate(SMFICTX *ctx, const char *filename, FILE *sendmail, const char *clamdMessage);
472
+static	void	setsubject(SMFICTX *ctx, const char *virusname);
472 473
 
473 474
 static	char	clamav_version[128];
474 475
 static	int	fflag = 0;	/* force a scan, whatever */
... ...
@@ -550,6 +554,16 @@ static	int	child_timeout = 60;	/* number of seconds to wait for
550 550
 					 * a child to die. Set to 0 to
551 551
 					 * wait forever
552 552
 					 */
553
+static	int	dont_wait = 0;	/*
554
+				 * If 1 send retry later to the remote end
555
+				 * if max_chilren is exceeded, otherwise we
556
+				 * wait for the number to go down
557
+				 */
558
+static	int	advisory = 0;	/*
559
+				 * Run clamav-milter in advisory mode - viruses
560
+				 * are flagged rather than deleted. Incompatible
561
+				 * with quarantine options
562
+				 */
553 563
 short	use_syslog = 0;
554 564
 static	const	char	*pidFile;
555 565
 static	int	logVerbose = 0;
... ...
@@ -581,11 +595,13 @@ help(void)
581 581
 	printf("\n\tclamav-milter version %s\n", CM_VERSION);
582 582
 	puts("\tCopyright (C) 2004 Nigel Horne <njh@despammed.com>\n");
583 583
 
584
+	puts("\t--advisory\t\t-A\tFlag viruses rather than deleting them.");
584 585
 	puts("\t--bounce\t\t-b\tSend a failure message to the sender.");
585 586
 	puts("\t--config-file=FILE\t-c FILE\tRead configuration from FILE.");
586 587
 	puts("\t--debug\t\t\t-D\tPrint debug messages.");
587 588
 	puts("\t--dont-log-clean\t-C\tDon't add an entry to syslog that a mail is clean.");
588 589
 	puts("\t--dont-scan-on-error\t-d\tPass e-mails through unscanned if a system error occurs.");
590
+	puts("\t--dont-wait\t\t\tAsk remote end to resend if max-children exceeded.");
589 591
 	puts("\t--from=EMAIL\t\t-a EMAIL\tError messages come from here.");
590 592
 	puts("\t--force-scan\t\t-f\tForce scan all messages (overrides (-o and -l).");
591 593
 	puts("\t--help\t\t\t-h\tThis message.");
... ...
@@ -604,7 +620,7 @@ help(void)
604 604
 	puts("\t--sign\t\t\t-S\tAdd a hard-coded signature to each scanned message.");
605 605
 	puts("\t--signature-file=FILE\t-F FILE\tLocation of signature file.");
606 606
 	puts("\t--template-file=FILE\t-t FILE\tLocation of e-mail template file.");
607
-	puts("\t--timeout=SECS\t-T SECS\tTimeout waiting to childen to die.");
607
+	puts("\t--timeout=SECS\t\t-T SECS\tTimeout waiting to childen to die.");
608 608
 	puts("\t--version\t\t-V\tPrint the version number of this software.");
609 609
 #ifdef	CL_DEBUG
610 610
 	puts("\t--debug-level=n\t\t-x n\tSets the debug level to 'n'.");
... ...
@@ -653,9 +669,9 @@ main(int argc, char **argv)
653 653
 	for(;;) {
654 654
 		int opt_index = 0;
655 655
 #ifdef	CL_DEBUG
656
-		const char *args = "a:bc:CDfF:lm:nNop:PqQ:dhHs:St:T:U:Vx:";
656
+		const char *args = "a:Abc:CDfF:lm:nNop:PqQ:dhHs:St:T:U:Vx:";
657 657
 #else
658
-		const char *args = "a:bc:CDfF:lm:nNop:PqQ:dhHs:St:T:U:V";
658
+		const char *args = "a:Abc:CDfF:lm:nNop:PqQ:dhHs:St:T:U:V";
659 659
 #endif
660 660
 
661 661
 		static struct option long_options[] = {
... ...
@@ -663,6 +679,9 @@ main(int argc, char **argv)
663 663
 				"from", 1, NULL, 'a'
664 664
 			},
665 665
 			{
666
+				"advisory", 0, NULL, 'A'
667
+			},
668
+			{
666 669
 				"bounce", 0, NULL, 'b'
667 670
 			},
668 671
 			{
... ...
@@ -675,6 +694,9 @@ main(int argc, char **argv)
675 675
 				"dont-scan-on-error", 0, NULL, 'd'
676 676
 			},
677 677
 			{
678
+				"dont-wait", 0, NULL, 'w'
679
+			},
680
+			{
678 681
 				"debug", 0, NULL, 'D'
679 682
 			},
680 683
 			{
... ...
@@ -758,6 +780,10 @@ main(int argc, char **argv)
758 758
 			case 'a':	/* e-mail errors from here */
759 759
 				from = optarg;
760 760
 				break;
761
+			case 'A':
762
+				advisory++;
763
+				smfilter.xxfi_flags |= SMFIF_CHGHDRS;
764
+				break;
761 765
 			case 'b':	/* bounce worms/viruses */
762 766
 				bflag++;
763 767
 				break;
... ...
@@ -837,6 +863,9 @@ main(int argc, char **argv)
837 837
 			case 'V':
838 838
 				puts(clamav_version);
839 839
 				return EX_OK;
840
+			case 'w':
841
+				dont_wait++;
842
+				break;
840 843
 #ifdef	CL_DEBUG
841 844
 			case 'x':
842 845
 				debug_level = atoi(optarg);
... ...
@@ -906,16 +935,24 @@ main(int argc, char **argv)
906 906
 		} else
907 907
 			fprintf(stderr, "%s: running as root is not recommended\n", argv[0]);
908 908
 	}
909
+	if(advisory && quarantine) {
910
+		fprintf(stderr, "%s: Advisory mode doesn't work with quarantine mode\n", argv[0]);
911
+		return EX_USAGE;
912
+	}
909 913
 	if(quarantine_dir) {
910 914
 		struct stat statb;
911 915
 
916
+		if(advisory) {
917
+			fprintf(stderr, "%s: Advisory mode doesn't work with quarantine directories\n", argv[0]);
918
+			return EX_USAGE;
919
+		}
912 920
 		if(access(quarantine_dir, W_OK) < 0) {
913 921
 			perror(quarantine_dir);
914
-			return EX_CONFIG;
922
+			return EX_USAGE;
915 923
 		}
916 924
 		if(stat(quarantine_dir, &statb) < 0) {
917 925
 			perror(quarantine_dir);
918
-			return EX_CONFIG;
926
+			return EX_USAGE;
919 927
 		}
920 928
 		/*
921 929
 		 * Quit if the quarantine directory is publically readable
... ...
@@ -1587,6 +1624,14 @@ clamfi_envfrom(SMFICTX *ctx, char **argv)
1587 1587
 					"hit max-children limit (%u >= %u): waiting for some to exit",
1588 1588
 					n_children, max_children);
1589 1589
 
1590
+			if(dont_wait) {
1591
+				pthread_mutex_unlock(&n_children_mutex);
1592
+				/*
1593
+				 * TODO: use smfi_setreply to send a useful
1594
+				 * message to the remote SMTP client
1595
+				 */
1596
+				return SMFIS_TEMPFAIL;
1597
+			}
1590 1598
 			/*
1591 1599
 			 * Wait for an amount of time for a child to go (default
1592 1600
 			 * 60 seconds).
... ...
@@ -2228,17 +2273,11 @@ clamfi_eom(SMFICTX *ctx)
2228 2228
 					syslog(LOG_DEBUG, "Can't set quarantine user %s", quarantine);
2229 2229
 				else
2230 2230
 					cli_warnmsg("Can't set quarantine user %s\n", quarantine);
2231
-			} else {
2232
-				char subject[128];
2233
-
2234
-				/*
2235
-				 * FIXME: doesn't work if there's no subject
2236
-				 */
2237
-				snprintf(subject, sizeof(subject) - 1,
2238
-					"[Virus] %s", virusname);
2239
-				smfi_chgheader(ctx, "Subject", 1, subject);
2240
-			}
2241
-		} else if(rejectmail) {
2231
+			} else
2232
+				setsubject(ctx, virusname);
2233
+		} else if(advisory)
2234
+			setsubject(ctx, virusname);
2235
+		else if(rejectmail) {
2242 2236
 			if(privdata->discard)
2243 2237
 				rc = SMFIS_DISCARD;
2244 2238
 			else
... ...
@@ -3001,3 +3040,18 @@ sendtemplate(SMFICTX *ctx, const char *filename, FILE *sendmail, const char *cla
3001 3001
 
3002 3002
 	return 0;
3003 3003
 }
3004
+
3005
+/*
3006
+ * Store the name of the virus in the subject of the e-mail
3007
+ */
3008
+static void
3009
+setsubject(SMFICTX *ctx, const char *virusname)
3010
+{
3011
+	char subject[128];
3012
+
3013
+	/*
3014
+	 * FIXME: doesn't work if there's no subject
3015
+	 */
3016
+	snprintf(subject, sizeof(subject) - 1, "[Virus] %s", virusname);
3017
+	smfi_chgheader(ctx, "Subject", 1, subject);
3018
+}
... ...
@@ -53,6 +53,12 @@ configured with \-\-clamav-debug.
53 53
 Will be replaced by \-\-debug for compatability with other programs in the
54 54
 suite.
55 55
 .TP
56
+\fB-A, \-\-advisory\fR
57
+When in advisory mode, clamav\-milter flags emails with viruses but
58
+still forwards them. The default option is to stop viruses.
59
+.LP
60
+This mode is in compatible with \-\-quarantine and \-\-quarantine-dir.
61
+.TP
56 62
 \fB\-b, \-\-bounce\fR
57 63
 Send a failure message to the sender, and to the postmaster.
58 64
 [ \fBWarning\fR: most viruses and worms
... ...
@@ -150,6 +156,12 @@ in \fBclamav.conf\fR.
150 150
 .LP
151 151
 Most users will not need this option, if in doubt do not set it.
152 152
 .TP
153
+\fB\-\-dont\-wait\fR
154
+Tells clamav\-milter what do to if the max-children number is exceeded.
155
+Usuaully clamav\-milter waits until a child dies or the timeout value has been
156
+exceeded, which ever comes first, however with dont-wait enabled, clamav\-milter
157
+will inform the remote SMTP client to retry later.
158
+.TP
153 159
 \fB\-\-template\-file=file \-t file\fR
154 160
 File points to a file whose contents is sent as the warning message whenever a
155 161
 virus is intercepted.
... ...
@@ -165,6 +177,8 @@ Used in conjuction with max\-children. If clamav\-milter waits for more than
165 165
 \fIn\fR seconds (default 60) it proceeds with scanning. Setting \fIn\fR to zero
166 166
 will turn off the timeout and clamav\-milter will wait indefinately for the
167 167
 scanning to quit. In practice the timeout set by sendmail will then take over.
168
+.SH "BUGS"
169
+There is no support for IPv6.
168 170
 .SH "EXAMPLES"
169 171
 .LP
170 172
 clamav\-milter \-ol local:/var/run/clamav/clmilter.sock