Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 25 Oct 2009 10:00:23 GMT
From:      Alex Dupre <ale@FreeBSD.org>
To:        FreeBSD-gnats-submit@FreeBSD.org
Subject:   ports/139962: [Patch] mail/vpopmail: fix maildir++ quota with spamassassin
Message-ID:  <200910251000.n9PA0Nqb008381@freefall.freebsd.org>
Resent-Message-ID: <200910251600.n9PG09TK019514@freefall.freebsd.org>

next in thread | raw e-mail | index | archive | help

>Number:         139962
>Category:       ports
>Synopsis:       [Patch] mail/vpopmail: fix maildir++ quota with spamassassin
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    freebsd-ports-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Sun Oct 25 16:00:08 UTC 2009
>Closed-Date:
>Last-Modified:
>Originator:     Alex Dupre
>Release:        FreeBSD 8.0-RC1 i386
>Organization:
>Environment:
System: FreeBSD freefall.freebsd.org 8.0-RC1 FreeBSD 8.0-RC1 #41 r197738: Sun Oct 4 11:00:31 UTC 2009 simon@freefall.freebsd.org:/usr/src/sys/i386/compile/FREEFALL i386


	
>Description:
When spamassassin is used, the Maildir++ S=nnn value is different from the actual message size,
since SA modify the original message and the filename is constructed before.
When I initially wrote the patch I didn't care, but actually it's better to be coherent here
and set the correct message size.
	
>How-To-Repeat:
	
>Fix:
Stat the 'tmp' file after processing and use the real size to create the 'new' filename.

	

--- vpopmail.diff begins here ---
Index: files/patch-vdelivermail.c
===================================================================
RCS file: /home/pcvs/ports/mail/vpopmail/files/patch-vdelivermail.c,v
retrieving revision 1.11
diff -u -r1.11 patch-vdelivermail.c
--- files/patch-vdelivermail.c	16 Mar 2009 13:51:23 -0000	1.11
+++ files/patch-vdelivermail.c	25 Oct 2009 09:51:41 -0000
@@ -1,8 +1,5 @@
-Add SpamAssassin support.
-Drop the unneeded MAX_ENV_BUFF definition.
-
---- a/vdelivermail.c
-+++ b/vdelivermail.c
+--- vdelivermail.c.orig	2007-11-18 06:15:19.000000000 +0100
++++ vdelivermail.c	2009-10-25 10:44:40.000000000 +0100
 @@ -74,6 +74,7 @@
  int is_spam();
  #endif
@@ -70,8 +67,23 @@
      return 0;
  }
  
-@@ -495,6 +513,11 @@
+@@ -481,8 +499,8 @@
+ int deliver_to_maildir (
+     const char *maildir,
+     const char *extra_headers,
+-    int read_fd,
+-    ssize_t msgsize)
++    int read_fd
++    )
+ {
+ #ifdef HOST_NAME_MAX
+   char hostname[HOST_NAME_MAX];
+@@ -493,21 +511,25 @@
+   char local_file_tmp[FILE_SIZE];
+   char local_file_new[FILE_SIZE];
    size_t headerlen;
++  struct stat sb;
++  size_t msgsize;
    int write_fd;
    char quota[80];
 +#ifdef SPAM_JUNKFOLDER
@@ -81,10 +93,40 @@
 +#endif
  
      headerlen = strlen (extra_headers);
-     msgsize += headerlen;
-@@ -557,6 +580,24 @@
+-    msgsize += headerlen;
+     
+     /* Format the email file name */
+     /* we get the whole hostname, even though we only use 32 chars of it */
+     gethostname(hostname, sizeof(hostname));
+     pid = (long unsigned) getpid();
+     tm = (long unsigned) time((time_t *) NULL);
+-    snprintf(local_file_tmp, sizeof(local_file_tmp), "%stmp/%lu.%lu.%.32s,S=%lu",
+-        maildir, tm, pid, hostname, (long unsigned) msgsize);
+-    snprintf(local_file_new, sizeof(local_file_new), "%snew/%lu.%lu.%.32s,S=%lu",
+-        maildir, tm, pid, hostname, (long unsigned) msgsize);
++    snprintf(local_file_tmp, sizeof(local_file_tmp), "%stmp/%lu.%lu.%.32s",
++        maildir, tm, pid, hostname);
+ 
+     read_quota_from_maildir (maildir, quota, sizeof(quota));
+ 
+@@ -548,6 +570,9 @@
+ #endif
+         close (write_fd) == 0 ) {
+ 
++        if (stat(local_file_tmp, &sb) == -1)
++            DeleteMail = 1;
++
+ 	if(DeleteMail == 1) {
+ 	    if (unlink(local_file_tmp) != 0) {
+                 printf("unlink failed %s errno = %d\n", local_file_tmp, errno);
+@@ -556,7 +581,29 @@
+             return(0);
  	}
  
++        msgsize = sb.st_size;
++        snprintf(local_file_new, sizeof(local_file_new), "%snew/%lu.%lu.%.32s,S=%lu",
++            maildir, tm, pid, hostname, (long unsigned) msgsize);
++
          /* if this succeeds link the file to the new directory */
 +#ifdef SPAM_JUNKFOLDER
 +        if (MoveMail == 1) {
@@ -107,7 +149,7 @@
          if ( link( local_file_tmp, local_file_new ) == 0 ) {
              /* file was successfully delivered, remove temp file */
              if ( unlink(local_file_tmp) != 0 ) {
-@@ -616,6 +657,9 @@
+@@ -616,6 +663,9 @@
      /* rewind the message */
      lseek(0,0L,SEEK_SET);
  
@@ -117,7 +159,16 @@
      /* This is an command */
      if ( *address == '|' ) { 
  
-@@ -895,9 +939,6 @@
+@@ -723,7 +773,7 @@
+                 email);
+         }
+     
+-        switch (deliver_to_maildir (address, DeliveredTo, 0, message_size)) {
++        switch (deliver_to_maildir (address, DeliveredTo, 0)) {
+             case -1:
+                 vexiterr (EXIT_OVERQUOTA, "user is over quota");
+                 break;
+@@ -895,9 +945,6 @@
   */
  void run_command(char *prog)
  {
@@ -127,7 +178,16 @@
   int child;
   char *(args[4]);
   int wstat;
-@@ -1211,19 +1252,22 @@
+@@ -1183,7 +1230,7 @@
+             maildir_to_email(newdir), date_header());
+     }
+ 
+-    err = deliver_to_maildir (dir, DeliveredTo, read_fd, sb.st_size);
++    err = deliver_to_maildir (dir, DeliveredTo, read_fd);
+ 
+     close (read_fd);
+     
+@@ -1211,19 +1258,22 @@
   *   * in the email headers for X-Spam-Level: which
   *    * we put in each spam email
   *     *
@@ -154,7 +214,7 @@
  
           /* check for blank line, end of headers */
           for(k=j,found=0;k<i;++k) {
-@@ -1246,13 +1290,19 @@
+@@ -1246,13 +1296,19 @@
           }
           if ( found == 0 ) {
             InHeaders=0;
--- vpopmail.diff ends here ---


>Release-Note:
>Audit-Trail:
>Unformatted:



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200910251000.n9PA0Nqb008381>