SPF: rewrote code to work with 1.2.x libsfp2 series. SRS: upgraded to latest patch...
authorTom Kistner <tom@duncanthrax.net>
Tue, 24 May 2005 08:15:01 +0000 (08:15 +0000)
committerTom Kistner <tom@duncanthrax.net>
Tue, 24 May 2005 08:15:01 +0000 (08:15 +0000)
18 files changed:
src/OS/os.h-cygwin
src/src/auths/auth-spa.h
src/src/deliver.c
src/src/demime.c
src/src/drtables.c
src/src/globals.c
src/src/globals.h
src/src/malware.c
src/src/readconf.c
src/src/regex.c
src/src/routers/redirect.c
src/src/routers/redirect.h
src/src/spf.c
src/src/spf.h
src/src/spool_mbox.c
src/src/srs.c
src/src/structs.h
src/src/verify.c

index ebd9c848b4df88da37d941cdd5fea624a9306d76..591f0965ed648dd803e267b289ac0df1b71b56ca 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/OS/os.h-cygwin,v 1.1 2004/10/06 15:07:39 ph10 Exp $ */
+/* $Cambridge: exim/src/OS/os.h-cygwin,v 1.2 2005/05/24 08:15:01 tom Exp $ */
 
 /* Exim: OS-specific C header file for Cygwin */
 
@@ -27,7 +27,7 @@ int cygwin_setgid(gid_t gid );
 extern unsigned int cygwin_WinVersion;
 
 #define BASE_62 36  /* Windows aliases lower and upper cases in filenames.
-                      Consider reducing MAX_LOCALHOST_NUMBER */
+           Consider reducing MAX_LOCALHOST_NUMBER */
 #define CRYPT_H
 #define HAVE_MMAP
 #define HAVE_SYS_VFS_H
index da67178ffc0a1ad7c34209a8fa45e8238ec338bf..72936ca233858e08c3dd2753eb05ca638d447db7 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/auths/auth-spa.h,v 1.3 2005/02/17 11:58:27 ph10 Exp $ */
+/* $Cambridge: exim/src/src/auths/auth-spa.h,v 1.4 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -32,49 +32,49 @@ typedef unsigned char  uint8x;
 
 typedef struct
 {
-       uint16x        len;
-       uint16x        maxlen;
-       uint32x        offset;
+       uint16x         len;
+       uint16x         maxlen;
+       uint32x         offset;
 } SPAStrHeader;
 
 typedef struct
 {
-       char           ident[8];
-       uint32x        msgType;
+       char         ident[8];
+       uint32x         msgType;
        SPAStrHeader    uDomain;
-       uint32x        flags;
-       uint8x         challengeData[8];
-       uint8x         reserved[8];
+       uint32x         flags;
+       uint8x         challengeData[8];
+       uint8x         reserved[8];
        SPAStrHeader    emptyString;
-       uint8x         buffer[1024];
-       uint32x        bufIndex;
+       uint8x         buffer[1024];
+       uint32x         bufIndex;
 } SPAAuthChallenge;
 
 
 typedef struct
 {
-       char           ident[8];
-       uint32x        msgType;
-       uint32x        flags;
+       char         ident[8];
+       uint32x         msgType;
+       uint32x         flags;
        SPAStrHeader    user;
        SPAStrHeader    domain;
-       uint8x         buffer[1024];
-       uint32x        bufIndex;
+       uint8x         buffer[1024];
+       uint32x         bufIndex;
 } SPAAuthRequest;
 
 typedef struct
 {
-       char           ident[8];
-       uint32x        msgType;
+       char         ident[8];
+       uint32x         msgType;
        SPAStrHeader    lmResponse;
        SPAStrHeader    ntResponse;
        SPAStrHeader    uDomain;
        SPAStrHeader    uUser;
        SPAStrHeader    uWks;
        SPAStrHeader    sessionKey;
-       uint32x        flags;
-       uint8x         buffer[1024];
-       uint32x        bufIndex;
+       uint32x         flags;
+       uint8x         buffer[1024];
+       uint32x         bufIndex;
 } SPAAuthResponse;
 
 #define spa_request_length(ptr) (((ptr)->buffer - (uint8x*)(ptr)) + (ptr)->bufIndex)
index a7b367d800433951688d66a815905437a1d2552e..d9bf21a4c3fd68fddbcc6107c081448f61e9b4e0 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/deliver.c,v 1.14 2005/04/28 13:06:32 ph10 Exp $ */
+/* $Cambridge: exim/src/src/deliver.c,v 1.15 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -878,6 +878,11 @@ if (result == OK)
   if ((log_extra_selector & LX_sender_on_delivery) != 0)
     s = string_append(s, &size, &ptr, 3, US" F=<", sender_address, US">");
 
+  #ifdef EXPERIMENTAL_SRS
+  if(addr->p.srs_sender)
+    s = string_append(s, &size, &ptr, 3, US" SRS=<", addr->p.srs_sender, US">");
+  #endif
+
   /* You might think that the return path must always be set for a successful
   delivery; indeed, I did for some time, until this statement crashed. The case
   when it is not set is for a delivery to /dev/null which is optimised by not
@@ -1537,8 +1542,14 @@ transport_instance *tp = addr->transport;
 /* Set up the return path from the errors or sender address. If the transport
 has its own return path setting, expand it and replace the existing value. */
 
-return_path = (addr->p.errors_address != NULL)?
-  addr->p.errors_address : sender_address;
+if(addr->p.errors_address != NULL)
+  return_path = addr->p.errors_address;
+#ifdef EXPERIMENTAL_SRS
+else if(addr->p.srs_sender != NULL)
+  return_path = addr->p.srs_sender;
+#endif
+else
+  return_path = sender_address;
 
 if (tp->return_path != NULL)
   {
@@ -3528,8 +3539,14 @@ for (delivery_count = 0; addr_remote != NULL; delivery_count++)
   /* Compute the return path, expanding a new one if required. The old one
   must be set first, as it might be referred to in the expansion. */
 
-  return_path = (addr->p.errors_address != NULL)?
-    addr->p.errors_address : sender_address;
+  if(addr->p.errors_address != NULL)
+    return_path = addr->p.errors_address;
+#ifdef EXPERIMENTAL_SRS
+  else if(addr->p.srs_sender != NULL)
+    return_path = addr->p.srs_sender;
+#endif
+  else
+    return_path = sender_address;
 
   if (tp->return_path != NULL)
     {
index 961a2e046cf5b315ebae19f0697f968f239bac08..66c9f17b381d1ba8af490e7927e3786ccc75ec60 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/demime.c,v 1.4 2005/02/17 11:58:26 ph10 Exp $ */
+/* $Cambridge: exim/src/src/demime.c,v 1.5 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -452,7 +452,7 @@ int mime_check_boundary(uschar *line, struct boundary *boundaries) {
     for (i = 2; i < Ustrlen(line); i++) {
       if ((line[i] != ' ') && (line[i] != '\t')) {
         workbuf[j] = line[i];
-             j++;
+        j++;
       };
     };
     workbuf[j+1]='\0';
index 67a42eedc888fb4277e6ea797aab93ff1299cbc1..686b395297a40e6d2269f4556b189869eb9bdad4 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/drtables.c,v 1.2 2005/01/04 10:00:42 ph10 Exp $ */
+/* $Cambridge: exim/src/src/drtables.c,v 1.3 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -536,7 +536,7 @@ auth_info auths_available[] = {
 
 #ifdef AUTH_CYRUS_SASL
   {
-  US"cyrus_sasl",                           /* lookup name */
+  US"cyrus_sasl",           /* lookup name */
   auth_cyrus_sasl_options,
   &auth_cyrus_sasl_options_count,
   &auth_cyrus_sasl_option_defaults,
index 9ad36daf132c1abd47c4f15e374c8da4a72d9af8..2f6b5fdda27e0a63bbb0973b8d22a027db58229e 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/globals.c,v 1.26 2005/05/23 16:58:56 fanf2 Exp $ */
+/* $Cambridge: exim/src/src/globals.c,v 1.27 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -282,6 +282,9 @@ address_item address_defaults = {
     NULL,               /* errors_address */
     NULL,               /* extra_headers */
     NULL,               /* remove_headers */
+#ifdef EXPERIMENTAL_SRS
+    NULL,               /* srs_sender */
+#endif
   }
 };
 
@@ -1049,10 +1052,16 @@ uschar *spool_directory        = US SPOOL_DIRECTORY
 uschar *srs_config             = NULL;
 uschar *srs_db_address         = NULL;
 uschar *srs_db_key             = NULL;
+int     srs_hashlength         = 6;
+int     srs_hashmin            = -1;
+int     srs_maxage             = 31;
 uschar *srs_orig_recipient     = NULL;
 uschar *srs_orig_sender        = NULL;
 uschar *srs_recipient          = NULL;
+uschar *srs_secrets            = NULL;
 uschar *srs_status             = NULL;
+BOOL    srs_usehash            = TRUE;
+BOOL    srs_usetimestamp       = TRUE;
 #endif
 int     string_datestamp_offset= -1;
 BOOL    strip_excess_angle_brackets = FALSE;
index 58538975d6154ff0c5fce95224cce188972cc7ea..63f9059b639cd32846378ee690be6ea4396ef3a7 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/globals.h,v 1.18 2005/05/23 16:58:56 fanf2 Exp $ */
+/* $Cambridge: exim/src/src/globals.h,v 1.19 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -656,10 +656,16 @@ extern uschar *spool_directory;        /* Name of spool directory */
 extern uschar *srs_config;             /* SRS config secret:max age:hash length:use timestamp:use hash */
 extern uschar *srs_db_address;         /* SRS db address */
 extern uschar *srs_db_key;             /* SRS db key */
+extern int     srs_hashlength;         /* SRS hash length */
+extern int     srs_hashmin;            /* SRS minimum hash length */
+extern int     srs_maxage;             /* SRS max age */
 extern uschar *srs_orig_sender;        /* SRS original sender */
 extern uschar *srs_orig_recipient;     /* SRS original recipient */
 extern uschar *srs_recipient;          /* SRS recipient */
+extern uschar *srs_secrets;            /* SRS secrets list */
 extern uschar *srs_status;             /* SRS staus */
+extern BOOL    srs_usehash;            /* SRS use hash flag */
+extern BOOL    srs_usetimestamp;       /* SRS use timestamp flag */
 #endif
 extern int     string_datestamp_offset;/* After insertion by string_format */
 extern BOOL    strip_excess_angle_brackets; /* Surrounding route-addrs */
index 1cc6aea5c9e8ffe11035853fc6ccd2c2a5807075..153670d0e3a736a7ee93f5f03b3f5e2761beab64 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/malware.c,v 1.7 2005/02/17 11:58:26 ph10 Exp $ */
+/* $Cambridge: exim/src/src/malware.c,v 1.8 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -135,273 +135,273 @@ int malware(uschar **listptr) {
       return DEFER;
     };
 
-       /* "drweb" scanner type ----------------------------------------------- */
-       /* v0.1 - added support for tcp sockets                                 */
-       /* v0.0 - initial release -- support for unix sockets                   */
-       if (strcmpic(scanner_name,US"drweb") == 0) {
-               uschar *drweb_options;
-               uschar drweb_options_buffer[1024];
-               uschar drweb_options_default[] = "/usr/local/drweb/run/drwebd.sock";
-               struct sockaddr_un server;
-               int sock, result, ovector[30];
-               unsigned int port, fsize;
-               uschar tmpbuf[1024], *drweb_fbuf;
-               uschar scanrequest[1024];
-               uschar drweb_match_string[128];
-               int drweb_rc, drweb_cmd, drweb_flags = 0x0000, drweb_fd,
-                   drweb_vnum, drweb_slen, drweb_fin = 0x0000;
-               unsigned long bread;
-               uschar hostname[256];
-               struct hostent *he;
-               struct in_addr in;
-               pcre *drweb_re;
-
-               if ((drweb_options = string_nextinlist(&av_scanner_work, &sep,
-                       drweb_options_buffer, sizeof(drweb_options_buffer))) == NULL) {
-                       /* no options supplied, use default options */
-                       drweb_options = drweb_options_default;
-               };
-
-               if (*drweb_options != '/') {
-
-                       /* extract host and port part */
-                       if( sscanf(CS drweb_options, "%s %u", hostname, &port) != 2 ) {
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: invalid socket '%s'", drweb_options);
-                               return DEFER;
-                       }
-
-                       /* Lookup the host */
-                       if((he = gethostbyname(CS hostname)) == 0) {
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: failed to lookup host '%s'", hostname);
-                               return DEFER;
-                       }
-
-                       in = *(struct in_addr *) he->h_addr_list[0];
-
-                       /* Open the drwebd TCP socket */
-                       if ( (sock = ip_socket(SOCK_STREAM, AF_INET)) < 0) {
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: unable to acquire socket (%s)",
-                                       strerror(errno));
-                               return DEFER;
-                       }
-
-                       if (ip_connect(sock, AF_INET, (uschar*)inet_ntoa(in), port, 5) < 0) {
-                               close(sock);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: connection to %s, port %u failed (%s)",
-                                       inet_ntoa(in), port, strerror(errno));
-                               return DEFER;
-                       }
-
-                       /* prepare variables */
-                       drweb_cmd = htonl(DRWEBD_SCAN_CMD);
-                       drweb_flags = htonl(DRWEBD_RETURN_VIRUSES | DRWEBD_IS_MAIL);
-                       snprintf(CS scanrequest, 1024,CS"%s/scan/%s/%s.eml",
-                                   spool_directory, message_id, message_id);
-
-                       /* calc file size */
-                       drweb_fd = open(CS scanrequest, O_RDONLY);
-                       if (drweb_fd == -1) {
-                               close(sock);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: can't open spool file %s: %s",
-                                       scanrequest, strerror(errno));
-                               return DEFER;
-                       }
-                       fsize = lseek(drweb_fd, 0, SEEK_END);
-                       if (fsize == -1) {
-                               close(sock);
-                               close(drweb_fd);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: can't seek spool file %s: %s",
-                                       scanrequest, strerror(errno));
-                               return DEFER;
-                       }
-                       drweb_slen = htonl(fsize);
-                       lseek(drweb_fd, 0, SEEK_SET);
-
-                       /* send scan request */
-                       if ((send(sock, &drweb_cmd, sizeof(drweb_cmd), 0) < 0) ||
-                           (send(sock, &drweb_flags, sizeof(drweb_flags), 0) < 0) ||
-                           (send(sock, &drweb_fin, sizeof(drweb_fin), 0) < 0) ||
-                           (send(sock, &drweb_slen, sizeof(drweb_slen), 0) < 0)) {
-                               close(sock);
-                               close(drweb_fd);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: unable to send commands to socket (%s)", drweb_options);
-                               return DEFER;
-                       }
-
-                       drweb_fbuf = (uschar *) malloc (fsize);
-                       if (!drweb_fbuf) {
-                               close(sock);
-                               close(drweb_fd);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: unable to allocate memory %u for file (%s)",
-                                       fsize, scanrequest);
-                               return DEFER;
-                       }
-
-                       result = read (drweb_fd, drweb_fbuf, fsize);
-                       if (result == -1) {
-                               close(sock);
-                               close(drweb_fd);
-                               free(drweb_fbuf);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: can't read spool file %s: %s",
-                                       scanrequest, strerror(errno));
-                               return DEFER;
-                       }
-                       close(drweb_fd);
-
-                       /* send file body to socket */
-                       if (send(sock, drweb_fbuf, fsize, 0) < 0) {
-                               close(sock);
-                               free(drweb_fbuf);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: unable to send file body to socket (%s)", drweb_options);
-                               return DEFER;
-                       }
-                       close(drweb_fd);
-               }
-               else {
-                       /* open the drwebd UNIX socket */
-                       sock = socket(AF_UNIX, SOCK_STREAM, 0);
-                       if (sock < 0) {
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: can't open UNIX socket");
-                               return DEFER;
-                       }
-                       server.sun_family = AF_UNIX;
-                       Ustrcpy(server.sun_path, drweb_options);
-                       if (connect(sock, (struct sockaddr *) &server, sizeof(struct sockaddr_un)) < 0) {
-                               close(sock);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: unable to connect to socket (%s). errno=%d", drweb_options, errno);
-                               return DEFER;
-                       }
-
-                       /* prepare variables */
-                       drweb_cmd = htonl(DRWEBD_SCAN_CMD);
-                       drweb_flags = htonl(DRWEBD_RETURN_VIRUSES | DRWEBD_IS_MAIL);
-                       snprintf(CS scanrequest, 1024,CS"%s/scan/%s/%s.eml", spool_directory, message_id, message_id);
-                       drweb_slen = htonl(Ustrlen(scanrequest));
-
-                       /* send scan request */
-                       if ((send(sock, &drweb_cmd, sizeof(drweb_cmd), 0) < 0) ||
-                           (send(sock, &drweb_flags, sizeof(drweb_flags), 0) < 0) ||
-                           (send(sock, &drweb_slen, sizeof(drweb_slen), 0) < 0) ||
-                           (send(sock, scanrequest, Ustrlen(scanrequest), 0) < 0) ||
-                           (send(sock, &drweb_fin, sizeof(drweb_fin), 0) < 0)) {
-                               close(sock);
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: unable to send commands to socket (%s)", drweb_options);
-                               return DEFER;
-                       }
-               }
-
-               /* wait for result */
-               if ((bread = recv(sock, &drweb_rc, sizeof(drweb_rc), 0) != sizeof(drweb_rc))) {
-                       close(sock);
-                       log_write(0, LOG_MAIN|LOG_PANIC,
-                               "malware acl condition: drweb: unable to read return code");
-                       return DEFER;
-               }
-               drweb_rc = ntohl(drweb_rc);
-
-               if ((bread = recv(sock, &drweb_vnum, sizeof(drweb_vnum), 0) != sizeof(drweb_vnum))) {
-                       close(sock);
-                       log_write(0, LOG_MAIN|LOG_PANIC,
-                               "malware acl condition: drweb: unable to read the number of viruses");
-                       return DEFER;
-               }
-               drweb_vnum = ntohl(drweb_vnum);
-
-               /* "virus(es) found" if virus number is > 0 */
-               if (drweb_vnum)
-               {
-                       int i;
-                       uschar pre_malware_nb[256];
-
-                       malware_name = malware_name_buffer;
-
-                       /* setup default virus name */
-                       Ustrcpy(malware_name_buffer,"unknown");
-
-                       /* read and concatenate virus names into one string */
-                       for (i=0;i<drweb_vnum;i++)
-                       {
-                               /* read the size of report */
-                               if ((bread = recv(sock, &drweb_slen, sizeof(drweb_slen), 0) != sizeof(drweb_slen))) {
-                                       close(sock);
-                                       log_write(0, LOG_MAIN|LOG_PANIC,
-                                               "malware acl condition: drweb: cannot read report size");
-                                       return DEFER;
-                               };
-                               drweb_slen = ntohl(drweb_slen);
-
-                               /* read report body */
-                               if ((bread = recv(sock, tmpbuf, drweb_slen, 0)) != drweb_slen) {
-                                       close(sock);
-                                       log_write(0, LOG_MAIN|LOG_PANIC,
-                                               "malware acl condition: drweb: cannot read report string");
-                                       return DEFER;
-                               };
-                               tmpbuf[drweb_slen] = '\0';
-
-                               /* set up match regex, depends on retcode */
-                               Ustrcpy(drweb_match_string, "infected\\swith\\s*(.+?)$");
-
-                               drweb_re = pcre_compile( CS drweb_match_string,
-                                       PCRE_COPT,
-                                       (const char **)&rerror,
-                                       &roffset,
-                                       NULL );
-
-                               /* try matcher on the line, grab substring */
-                               result = pcre_exec(drweb_re, NULL, CS tmpbuf, Ustrlen(tmpbuf), 0, 0, ovector, 30);
-                               if (result >= 2) {
-                                       pcre_copy_substring(CS tmpbuf, ovector, result, 1, CS pre_malware_nb, 255);
-                               }
-                               /* the first name we just copy to malware_name */
-                               if (i==0)
-                                       Ustrcpy(CS malware_name_buffer, CS pre_malware_nb);
-                               else {
-                                       /* concatenate each new virus name to previous */
-                                       int slen = Ustrlen(malware_name_buffer);
-                                       if (slen < (slen+Ustrlen(pre_malware_nb))) {
-                                               Ustrcat(malware_name_buffer, "/");
-                                               Ustrcat(malware_name_buffer, pre_malware_nb);
-                                       }
-                               }
-                       }
-               }
-               else {
-                       char *drweb_s = NULL;
-
-                       if (drweb_rc & DERR_READ_ERR) drweb_s = "read error";
-                       if (drweb_rc & DERR_NOMEMORY) drweb_s = "no memory";
-                       if (drweb_rc & DERR_TIMEOUT)  drweb_s = "timeout";
-                       if (drweb_rc & DERR_BAD_CALL) drweb_s = "wrong command";
-                       /* retcodes DERR_SYMLINK, DERR_NO_REGFILE, DERR_SKIPPED.
-                        * DERR_TOO_BIG, DERR_TOO_COMPRESSED, DERR_SPAM,
-                        * DERR_CRC_ERROR, DERR_READSOCKET, DERR_WRITE_ERR
-                        * and others are ignored */
-                       if (drweb_s) {
-                               log_write(0, LOG_MAIN|LOG_PANIC,
-                                       "malware acl condition: drweb: drweb daemon retcode 0x%x (%s)", drweb_rc, drweb_s);
-                               close(sock);
-                               return DEFER;
-                       }
-                       /* no virus found */
-                       malware_name = NULL;
-               };
-               close(sock);
-       }
-       /* ----------------------------------------------------------------------- */
+  /* "drweb" scanner type ----------------------------------------------- */
+  /* v0.1 - added support for tcp sockets          */
+  /* v0.0 - initial release -- support for unix sockets      */
+  if (strcmpic(scanner_name,US"drweb") == 0) {
+    uschar *drweb_options;
+    uschar drweb_options_buffer[1024];
+    uschar drweb_options_default[] = "/usr/local/drweb/run/drwebd.sock";
+    struct sockaddr_un server;
+    int sock, result, ovector[30];
+    unsigned int port, fsize;
+    uschar tmpbuf[1024], *drweb_fbuf;
+    uschar scanrequest[1024];
+    uschar drweb_match_string[128];
+    int drweb_rc, drweb_cmd, drweb_flags = 0x0000, drweb_fd,
+        drweb_vnum, drweb_slen, drweb_fin = 0x0000;
+    unsigned long bread;
+    uschar hostname[256];
+    struct hostent *he;
+    struct in_addr in;
+    pcre *drweb_re;
+
+    if ((drweb_options = string_nextinlist(&av_scanner_work, &sep,
+      drweb_options_buffer, sizeof(drweb_options_buffer))) == NULL) {
+      /* no options supplied, use default options */
+      drweb_options = drweb_options_default;
+    };
+
+    if (*drweb_options != '/') {
+
+      /* extract host and port part */
+      if( sscanf(CS drweb_options, "%s %u", hostname, &port) != 2 ) {
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: invalid socket '%s'", drweb_options);
+        return DEFER;
+      }
+
+      /* Lookup the host */
+      if((he = gethostbyname(CS hostname)) == 0) {
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: failed to lookup host '%s'", hostname);
+        return DEFER;
+      }
+
+      in = *(struct in_addr *) he->h_addr_list[0];
+
+      /* Open the drwebd TCP socket */
+      if ( (sock = ip_socket(SOCK_STREAM, AF_INET)) < 0) {
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: unable to acquire socket (%s)",
+          strerror(errno));
+        return DEFER;
+      }
+
+      if (ip_connect(sock, AF_INET, (uschar*)inet_ntoa(in), port, 5) < 0) {
+        close(sock);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: connection to %s, port %u failed (%s)",
+          inet_ntoa(in), port, strerror(errno));
+        return DEFER;
+      }
+
+      /* prepare variables */
+      drweb_cmd = htonl(DRWEBD_SCAN_CMD);
+      drweb_flags = htonl(DRWEBD_RETURN_VIRUSES | DRWEBD_IS_MAIL);
+      snprintf(CS scanrequest, 1024,CS"%s/scan/%s/%s.eml",
+            spool_directory, message_id, message_id);
+
+      /* calc file size */
+      drweb_fd = open(CS scanrequest, O_RDONLY);
+      if (drweb_fd == -1) {
+        close(sock);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: can't open spool file %s: %s",
+          scanrequest, strerror(errno));
+        return DEFER;
+      }
+      fsize = lseek(drweb_fd, 0, SEEK_END);
+      if (fsize == -1) {
+        close(sock);
+        close(drweb_fd);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: can't seek spool file %s: %s",
+          scanrequest, strerror(errno));
+        return DEFER;
+      }
+      drweb_slen = htonl(fsize);
+      lseek(drweb_fd, 0, SEEK_SET);
+
+      /* send scan request */
+      if ((send(sock, &drweb_cmd, sizeof(drweb_cmd), 0) < 0) ||
+          (send(sock, &drweb_flags, sizeof(drweb_flags), 0) < 0) ||
+          (send(sock, &drweb_fin, sizeof(drweb_fin), 0) < 0) ||
+          (send(sock, &drweb_slen, sizeof(drweb_slen), 0) < 0)) {
+        close(sock);
+        close(drweb_fd);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: unable to send commands to socket (%s)", drweb_options);
+        return DEFER;
+      }
+
+      drweb_fbuf = (uschar *) malloc (fsize);
+      if (!drweb_fbuf) {
+        close(sock);
+        close(drweb_fd);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: unable to allocate memory %u for file (%s)",
+          fsize, scanrequest);
+        return DEFER;
+      }
+
+      result = read (drweb_fd, drweb_fbuf, fsize);
+      if (result == -1) {
+        close(sock);
+        close(drweb_fd);
+        free(drweb_fbuf);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: can't read spool file %s: %s",
+          scanrequest, strerror(errno));
+        return DEFER;
+      }
+      close(drweb_fd);
+
+      /* send file body to socket */
+      if (send(sock, drweb_fbuf, fsize, 0) < 0) {
+        close(sock);
+        free(drweb_fbuf);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: unable to send file body to socket (%s)", drweb_options);
+        return DEFER;
+      }
+      close(drweb_fd);
+    }
+    else {
+      /* open the drwebd UNIX socket */
+      sock = socket(AF_UNIX, SOCK_STREAM, 0);
+      if (sock < 0) {
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: can't open UNIX socket");
+        return DEFER;
+      }
+      server.sun_family = AF_UNIX;
+      Ustrcpy(server.sun_path, drweb_options);
+      if (connect(sock, (struct sockaddr *) &server, sizeof(struct sockaddr_un)) < 0) {
+        close(sock);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: unable to connect to socket (%s). errno=%d", drweb_options, errno);
+        return DEFER;
+      }
+
+      /* prepare variables */
+      drweb_cmd = htonl(DRWEBD_SCAN_CMD);
+      drweb_flags = htonl(DRWEBD_RETURN_VIRUSES | DRWEBD_IS_MAIL);
+      snprintf(CS scanrequest, 1024,CS"%s/scan/%s/%s.eml", spool_directory, message_id, message_id);
+      drweb_slen = htonl(Ustrlen(scanrequest));
+
+      /* send scan request */
+      if ((send(sock, &drweb_cmd, sizeof(drweb_cmd), 0) < 0) ||
+          (send(sock, &drweb_flags, sizeof(drweb_flags), 0) < 0) ||
+          (send(sock, &drweb_slen, sizeof(drweb_slen), 0) < 0) ||
+          (send(sock, scanrequest, Ustrlen(scanrequest), 0) < 0) ||
+          (send(sock, &drweb_fin, sizeof(drweb_fin), 0) < 0)) {
+        close(sock);
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: unable to send commands to socket (%s)", drweb_options);
+        return DEFER;
+      }
+    }
+
+    /* wait for result */
+    if ((bread = recv(sock, &drweb_rc, sizeof(drweb_rc), 0) != sizeof(drweb_rc))) {
+      close(sock);
+      log_write(0, LOG_MAIN|LOG_PANIC,
+        "malware acl condition: drweb: unable to read return code");
+      return DEFER;
+    }
+    drweb_rc = ntohl(drweb_rc);
+
+    if ((bread = recv(sock, &drweb_vnum, sizeof(drweb_vnum), 0) != sizeof(drweb_vnum))) {
+      close(sock);
+      log_write(0, LOG_MAIN|LOG_PANIC,
+        "malware acl condition: drweb: unable to read the number of viruses");
+      return DEFER;
+    }
+    drweb_vnum = ntohl(drweb_vnum);
+
+    /* "virus(es) found" if virus number is > 0 */
+    if (drweb_vnum)
+    {
+      int i;
+      uschar pre_malware_nb[256];
+
+      malware_name = malware_name_buffer;
+
+      /* setup default virus name */
+      Ustrcpy(malware_name_buffer,"unknown");
+
+      /* read and concatenate virus names into one string */
+      for (i=0;i<drweb_vnum;i++)
+      {
+        /* read the size of report */
+        if ((bread = recv(sock, &drweb_slen, sizeof(drweb_slen), 0) != sizeof(drweb_slen))) {
+          close(sock);
+          log_write(0, LOG_MAIN|LOG_PANIC,
+            "malware acl condition: drweb: cannot read report size");
+          return DEFER;
+        };
+        drweb_slen = ntohl(drweb_slen);
+
+        /* read report body */
+        if ((bread = recv(sock, tmpbuf, drweb_slen, 0)) != drweb_slen) {
+          close(sock);
+          log_write(0, LOG_MAIN|LOG_PANIC,
+            "malware acl condition: drweb: cannot read report string");
+          return DEFER;
+        };
+        tmpbuf[drweb_slen] = '\0';
+
+        /* set up match regex, depends on retcode */
+        Ustrcpy(drweb_match_string, "infected\\swith\\s*(.+?)$");
+
+        drweb_re = pcre_compile( CS drweb_match_string,
+          PCRE_COPT,
+          (const char **)&rerror,
+          &roffset,
+          NULL );
+
+        /* try matcher on the line, grab substring */
+        result = pcre_exec(drweb_re, NULL, CS tmpbuf, Ustrlen(tmpbuf), 0, 0, ovector, 30);
+        if (result >= 2) {
+          pcre_copy_substring(CS tmpbuf, ovector, result, 1, CS pre_malware_nb, 255);
+        }
+        /* the first name we just copy to malware_name */
+        if (i==0)
+          Ustrcpy(CS malware_name_buffer, CS pre_malware_nb);
+        else {
+          /* concatenate each new virus name to previous */
+          int slen = Ustrlen(malware_name_buffer);
+          if (slen < (slen+Ustrlen(pre_malware_nb))) {
+            Ustrcat(malware_name_buffer, "/");
+            Ustrcat(malware_name_buffer, pre_malware_nb);
+          }
+        }
+      }
+    }
+    else {
+      char *drweb_s = NULL;
+
+      if (drweb_rc & DERR_READ_ERR) drweb_s = "read error";
+      if (drweb_rc & DERR_NOMEMORY) drweb_s = "no memory";
+      if (drweb_rc & DERR_TIMEOUT)  drweb_s = "timeout";
+      if (drweb_rc & DERR_BAD_CALL) drweb_s = "wrong command";
+      /* retcodes DERR_SYMLINK, DERR_NO_REGFILE, DERR_SKIPPED.
+       * DERR_TOO_BIG, DERR_TOO_COMPRESSED, DERR_SPAM,
+       * DERR_CRC_ERROR, DERR_READSOCKET, DERR_WRITE_ERR
+       * and others are ignored */
+      if (drweb_s) {
+        log_write(0, LOG_MAIN|LOG_PANIC,
+          "malware acl condition: drweb: drweb daemon retcode 0x%x (%s)", drweb_rc, drweb_s);
+        close(sock);
+        return DEFER;
+      }
+      /* no virus found */
+      malware_name = NULL;
+    };
+    close(sock);
+  }
+  /* ----------------------------------------------------------------------- */
     else if (strcmpic(scanner_name,US"aveserver") == 0) {
       uschar *kav_options;
       uschar kav_options_buffer[1024];
@@ -1107,57 +1107,57 @@ int malware(uschar **listptr) {
             return DEFER;
           }
 
-         snprintf(CS scanrequest, 1024,CS"%s/scan/%s/%s.eml",
-           spool_directory, message_id, message_id);
-
-         /* calc file size */
-         clam_fd = open(CS scanrequest, O_RDONLY);
-         if (clam_fd == -1) {
-           log_write(0, LOG_MAIN|LOG_PANIC,
-                   "malware acl condition: clamd: can't open spool file %s: %s",
-                   scanrequest, strerror(errno));
-           return DEFER;
-         }
-         fsize = lseek(clam_fd, 0, SEEK_END);
-         if (fsize == -1) {
-           log_write(0, LOG_MAIN|LOG_PANIC,
-                   "malware acl condition: clamd: can't seek spool file %s: %s",
-                   scanrequest, strerror(errno));
-           return DEFER;
-         }
-         lseek(clam_fd, 0, SEEK_SET);
-
-         clamav_fbuf = (uschar *) malloc (fsize);
-         if (!clamav_fbuf) {
-           close(sockData);
-           close(clam_fd);
-           log_write(0, LOG_MAIN|LOG_PANIC,
-                   "malware acl condition: clamd: unable to allocate memory %u for file (%s)",
-                   fsize, scanrequest);
-           return DEFER;
-         }
-
-         result = read (clam_fd, clamav_fbuf, fsize);
-         if (result == -1) {
-           close(sockData);
-           close(clam_fd);
-           free(clamav_fbuf);
-           log_write(0, LOG_MAIN|LOG_PANIC,
-                   "malware acl condition: clamd: can't read spool file %s: %s",
-                   scanrequest, strerror(errno));
-           return DEFER;
-         }
-         close(clam_fd);
-
-         /* send file body to socket */
-         if (send(sockData, clamav_fbuf, fsize, 0) < 0) {
-           close(sockData);
-           free(clamav_fbuf);
-           log_write(0, LOG_MAIN|LOG_PANIC,
-             "malware acl condition: clamd: unable to send file body to socket (%s:%u)", hostname, port);
-           return DEFER;
-         }
-         free(clamav_fbuf);
+    snprintf(CS scanrequest, 1024,CS"%s/scan/%s/%s.eml",
+      spool_directory, message_id, message_id);
+
+    /* calc file size */
+    clam_fd = open(CS scanrequest, O_RDONLY);
+    if (clam_fd == -1) {
+      log_write(0, LOG_MAIN|LOG_PANIC,
+        "malware acl condition: clamd: can't open spool file %s: %s",
+        scanrequest, strerror(errno));
+      return DEFER;
+    }
+    fsize = lseek(clam_fd, 0, SEEK_END);
+    if (fsize == -1) {
+      log_write(0, LOG_MAIN|LOG_PANIC,
+        "malware acl condition: clamd: can't seek spool file %s: %s",
+        scanrequest, strerror(errno));
+      return DEFER;
+    }
+    lseek(clam_fd, 0, SEEK_SET);
+
+    clamav_fbuf = (uschar *) malloc (fsize);
+    if (!clamav_fbuf) {
+      close(sockData);
+      close(clam_fd);
+      log_write(0, LOG_MAIN|LOG_PANIC,
+        "malware acl condition: clamd: unable to allocate memory %u for file (%s)",
+        fsize, scanrequest);
+      return DEFER;
+    }
+
+    result = read (clam_fd, clamav_fbuf, fsize);
+    if (result == -1) {
+      close(sockData);
+      close(clam_fd);
+      free(clamav_fbuf);
+      log_write(0, LOG_MAIN|LOG_PANIC,
+        "malware acl condition: clamd: can't read spool file %s: %s",
+        scanrequest, strerror(errno));
+      return DEFER;
+    }
+    close(clam_fd);
+
+    /* send file body to socket */
+    if (send(sockData, clamav_fbuf, fsize, 0) < 0) {
+      close(sockData);
+      free(clamav_fbuf);
+      log_write(0, LOG_MAIN|LOG_PANIC,
+        "malware acl condition: clamd: unable to send file body to socket (%s:%u)", hostname, port);
+      return DEFER;
+    }
+    free(clamav_fbuf);
           close(sockData);
         }
       }
@@ -1223,7 +1223,7 @@ int malware(uschar **listptr) {
       /* Check the result. ClamAV Returns
          infected: -> "<filename>: <virusname> FOUND"
          not-infected: -> "<filename>: OK"
-               error: -> "<filename>: <errcode> ERROR */
+    error: -> "<filename>: <errcode> ERROR */
 
       if (!(*av_buffer)) {
         log_write(0, LOG_MAIN|LOG_PANIC,
@@ -1287,8 +1287,8 @@ int malware(uschar **listptr) {
                                             mksd_options_buffer,
                                             sizeof(mksd_options_buffer))) != NULL) {
         mksd_maxproc = (int) strtol(CS mksd_options, &mksd_options_end, 10);
-             if ((*mksd_options == '\0') || (*mksd_options_end != '\0') ||
-                 (mksd_maxproc < 1) || (mksd_maxproc > 32)) {
+        if ((*mksd_options == '\0') || (*mksd_options_end != '\0') ||
+      (mksd_maxproc < 1) || (mksd_maxproc > 32)) {
           log_write(0, LOG_MAIN|LOG_PANIC,
                     "malware acl condition: mksd: invalid option '%s'", mksd_options);
           return DEFER;
@@ -1444,7 +1444,7 @@ int mksd_parse_line (char *line)
           if (((p = strchr (line+4, ' ')) != NULL) && ((p-line) > 4)) {
             (*p) = '\0';
             Ustrcpy (malware_name_buffer, line+4);
-           malware_name = malware_name_buffer;
+      malware_name = malware_name_buffer;
             return OK;
           }
       }
index be935bd116bd8f3cb4d923997fbbce0c63b59336..6a6b3ba2ac288617dc27f37b3aebcddfaf3941ac 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/readconf.c,v 1.8 2005/05/10 10:19:11 ph10 Exp $ */
+/* $Cambridge: exim/src/src/readconf.c,v 1.9 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -339,6 +339,12 @@ static optionlist optionlist_config[] = {
   { "spool_directory",          opt_stringptr,   &spool_directory },
 #ifdef EXPERIMENTAL_SRS
   { "srs_config",               opt_stringptr,   &srs_config },
+  { "srs_hashlength",           opt_int,         &srs_hashlength },
+  { "srs_hashmin",              opt_int,         &srs_hashmin },
+  { "srs_maxage",               opt_int,         &srs_maxage },
+  { "srs_secrets",              opt_stringptr,   &srs_secrets },
+  { "srs_usehash",              opt_bool,        &srs_usehash },
+  { "srs_usetimestamp",         opt_bool,        &srs_usetimestamp },
 #endif
   { "strip_excess_angle_brackets", opt_bool,     &strip_excess_angle_brackets },
   { "strip_trailing_dot",       opt_bool,        &strip_trailing_dot },
index 7d2e366fc530f17bfb5ed506e494b86e019a5637..c811f439fddfe110cbd0ea4c0605065c4955a861 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/regex.c,v 1.4 2005/02/17 11:58:26 ph10 Exp $ */
+/* $Cambridge: exim/src/src/regex.c,v 1.5 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -113,7 +113,7 @@ int regex(uschar **listptr) {
     do {
       /* try matcher on the line */
       if (pcre_exec(re_list_item->re, NULL, CS linebuffer,
-                       (int)Ustrlen(linebuffer), 0, 0, NULL, 0) >= 0) {
+      (int)Ustrlen(linebuffer), 0, 0, NULL, 0) >= 0) {
         Ustrncpy(regex_match_string_buffer, re_list_item->pcre_text, 1023);
         regex_match_string = regex_match_string_buffer;
         if (mime_stream == NULL)
index 8e8fc876c5af80642aca54bf5c712c6174e55c44..641a5ef6ef9d147a384308d08bcbd1aa49eed413 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/routers/redirect.c,v 1.10 2005/04/28 13:06:32 ph10 Exp $ */
+/* $Cambridge: exim/src/src/routers/redirect.c,v 1.11 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -112,8 +112,10 @@ optionlist redirect_router_options[] = {
       (void *)offsetof(redirect_router_options_block, srs_alias) },
   { "srs_condition",      opt_stringptr,
       (void *)offsetof(redirect_router_options_block, srs_condition) },
-  { "srs_db",             opt_stringptr,
-      (void *)offsetof(redirect_router_options_block, srs_db) },
+  { "srs_dbinsert",       opt_stringptr,
+      (void *)offsetof(redirect_router_options_block, srs_dbinsert) },
+  { "srs_dbselect",       opt_stringptr,
+      (void *)offsetof(redirect_router_options_block, srs_dbselect) },
 #endif
   { "syntax_errors_text", opt_stringptr,
       (void *)offsetof(redirect_router_options_block, syntax_errors_text) },
@@ -152,9 +154,10 @@ redirect_router_options_block redirect_router_option_defaults = {
   NULL,        /* owngroups */
 #ifdef EXPERIMENTAL_SRS
   NULL,        /* srs */
-  NULL,        /* srs_condition */
-  NULL,        /* srs_db */
   NULL,        /* srs_alias */
+  NULL,        /* srs_condition */
+  NULL,        /* srs_dbinsert */
+  NULL,        /* srs_dbselect */
 #endif
   022,         /* modemask */
   RDO_REWRITE, /* bit_options */
@@ -529,6 +532,10 @@ addr_prop.errors_address = NULL;
 addr_prop.extra_headers = NULL;
 addr_prop.remove_headers = NULL;
 
+#ifdef EXPERIMENTAL_SRS
+addr_prop.srs_sender = NULL;
+#endif
+
 /* When verifying and testing addresses, the "logwrite" command in filters
 must be bypassed. */
 
@@ -555,8 +562,8 @@ if (!ugid.gid_set && pw != NULL)
   }
 
 #ifdef EXPERIMENTAL_SRS
-  /* For reverse SRS, fill the srs_recipient expandsion variable,
-  on failure, return decline/fail as relevant */
+  /* Perform SRS on recipient/return-path as required  */
+
   if(ob->srs != NULL)
   {
     BOOL usesrs = TRUE;
@@ -565,22 +572,78 @@ if (!ugid.gid_set && pw != NULL)
       usesrs = expand_check_condition(ob->srs_condition, "srs_condition expansion failed", NULL);
 
     if(usesrs)
-      if(Ustrcmp(ob->srs, "reverse") == 0 || Ustrcmp(ob->srs, "reverseandforward") == 0)
+    {
+      int srs_action, n_srs;
+      uschar *res;
+      uschar *usedomain;
+
+      /* What are we doing? */
+      if(Ustrcmp(ob->srs, "forward") == 0)
+        srs_action = 1;
+      else if(Ustrcmp(ob->srs, "reverseandforward") == 0)
       {
-        uschar *res;
-        int n_srs;
+        srs_action = 3;
 
+        if((ob->srs_dbinsert == NULL) ^ (ob->srs_dbselect == NULL))
+          return DEFER;
+      }
+      else if(Ustrcmp(ob->srs, "reverse") == 0)
+        srs_action = 2;
+
+      /* Reverse SRS */
+      if(srs_action & 2)
+      {
         srs_orig_recipient = addr->address;
+
         eximsrs_init();
-        if(ob->srs_db)
-          eximsrs_db_set(TRUE, ob->srs_db);
-        if((n_srs = eximsrs_reverse(&res, addr->address)) != OK)
+        if(ob->srs_dbselect)
+          eximsrs_db_set(TRUE, ob->srs_dbselect);
+// Comment this out for now...
+//        else
+//          eximsrs_db_set(TRUE, NULL);
+
+        if((n_srs = eximsrs_reverse(&res, addr->address)) == OK)
+        {
+          srs_recipient = res;
+          DEBUG(D_any)
+            debug_printf("SRS (reverse): Recipient '%s' rewritten to '%s'\n", srs_orig_recipient, srs_recipient);
+        }
+
+        eximsrs_done();
+
+        if(n_srs != OK)
           return n_srs;
-        srs_recipient = res;
+      }
+
+      /* Forward SRS */
+      /* No point in actually performing SRS if we are just verifying a recipient */
+      if((srs_action & 1) && !verify && (sender_address ? sender_address[0] != 0 : FALSE))
+      {
+
+        srs_orig_sender = sender_address;
+        eximsrs_init();
+        if(ob->srs_dbinsert)
+          eximsrs_db_set(FALSE, ob->srs_dbinsert);
+// Comment this out for now...
+//        else
+//          eximsrs_db_set(FALSE, NULL);
+
+        if(ob->srs_alias != NULL ? (usedomain = expand_string(ob->srs_alias)) == NULL : 1)
+          usedomain = deliver_domain;
+
+        if((n_srs = eximsrs_forward(&res, sender_address, usedomain)) == OK)
+        {
+          addr_prop.srs_sender = res;
+          DEBUG(D_any)
+            debug_printf("SRS (forward): Sender '%s' rewritten to '%s'\n", srs_orig_sender, res);
+        }
+
         eximsrs_done();
-        DEBUG(D_any)
-          debug_printf("SRS: Recipient '%s' rewritten to '%s'\n", srs_orig_recipient, srs_recipient);
+
+        if(n_srs != OK)
+          return n_srs;
       }
+    }
   }
 #endif
 
@@ -813,39 +876,6 @@ else
     (addr_prop.errors_address != NULL)? "\n" : "");
   }
 
-#ifdef EXPERIMENTAL_SRS
-  /* On successful redirection, check for SRS forwarding and adjust sender */
-  if(ob->srs != NULL)
-  {
-    BOOL usesrs = TRUE;
-
-    if(ob->srs_condition != NULL)
-      usesrs = expand_check_condition(ob->srs_condition, "srs_condition expansion failed", NULL);
-
-    if(usesrs)
-      if((Ustrcmp(ob->srs, "forward") == 0 || Ustrcmp(ob->srs, "reverseandforward") == 0) && !verify)
-      {
-        uschar *res;
-        uschar *usedomain;
-        int n_srs;
-
-        srs_orig_sender = sender_address;
-        eximsrs_init();
-        if(ob->srs_db)
-          eximsrs_db_set(FALSE, ob->srs_db);
-
-        if(ob->srs_alias != NULL ? (usedomain = expand_string(ob->srs_alias)) == NULL : 1)
-          usedomain = deliver_domain;
-
-        if((n_srs = eximsrs_forward(&res, sender_address, usedomain)) != OK)
-          return n_srs;
-        sender_address = res;
-        DEBUG(D_any)
-          debug_printf("SRS: Sender '%s' rewritten to '%s'\n", srs_orig_sender, sender_address);
-    }
-  }
-#endif
-
 /* Control gets here only when the address has been completely handled. Put the
 original address onto the succeed queue so that any retry items that get
 attached to it get processed. */
index bda2224a8628508b4c2fc9e7c7c2fd7b0303bda0..bc6ab974c4a3ee905faab12b6e2c65e13acd576d 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/routers/redirect.h,v 1.4 2005/04/06 14:40:24 ph10 Exp $ */
+/* $Cambridge: exim/src/src/routers/redirect.h,v 1.5 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -37,9 +37,10 @@ typedef struct {
 
 #ifdef EXPERIMENTAL_SRS
   uschar *srs;
-  uschar *srs_condition;
-  uschar *srs_db;
   uschar *srs_alias;
+  uschar *srs_condition;
+  uschar *srs_dbinsert;
+  uschar *srs_dbselect;
 #endif
 
   int   modemask;
index 1ef222affd231b3138a24f59166dcadc035849e7..6fd7445615ceb95a86087bbcceb1640dc860bfeb 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/spf.c,v 1.3 2005/02/17 11:58:26 ph10 Exp $ */
+/* $Cambridge: exim/src/src/spf.c,v 1.4 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
 #include "exim.h"
 #ifdef EXPERIMENTAL_SPF
 
-/* #include "spf.h" */
-
-SPF_config_t        spfcid = NULL;
-SPF_dns_config_t    spfdcid_resolv = NULL;
-SPF_dns_config_t    spfdcid = NULL;
-
+SPF_server_t    *spf_server = NULL;
+SPF_request_t   *spf_request = NULL;
+SPF_response_t  *spf_response = NULL;
+SPF_response_t  *spf_response_2mx = NULL;
 
 /* spf_init sets up a context that can be re-used for several
    messages on the same SMTP connection (that come from the
@@ -27,40 +25,27 @@ SPF_dns_config_t    spfdcid = NULL;
 int spf_init(uschar *spf_helo_domain, uschar *spf_remote_addr) {
   uschar *p;
 
-  /* paranoia */
-  spfcid = NULL;
-  spfdcid_resolv = NULL;
-  spfdcid = NULL;
+  spf_server = SPF_server_new(SPF_DNS_CACHE, 1);
 
-  spfcid = SPF_create_config();
-  if ( spfcid == NULL ) {
-    debug_printf("spf: SPF_create_config() failed.\n");
-         return 0;
+  if ( spf_server == NULL ) {
+    debug_printf("spf: SPF_server_new() failed.\n");
+    return 0;
   }
 
-  /* set up resolver */
-  spfdcid_resolv = SPF_dns_create_config_resolv(NULL, 0);
-  spfdcid = SPF_dns_create_config_cache(spfdcid_resolv, 8, 0);
-
-  if (spfdcid == NULL) {
-    debug_printf("spf: SPF_dns_create_config_cache() failed.\n");
-    spfcid = NULL;
-    spfdcid_resolv = NULL;
-         return 0;
-  }
+  spf_request = SPF_request_new(spf_server);
 
-  if (SPF_set_ip_str(spfcid, spf_remote_addr)) {
-    debug_printf("spf: SPF_set_ip_str() failed.\n");
-    spfcid = NULL;
-    spfdcid_resolv = NULL;
-         return 0;
+  if (SPF_request_set_ipv4_str(spf_request, spf_remote_addr)) {
+    debug_printf("spf: SPF_request_set_ipv4_str() failed.\n");
+    spf_server = NULL;
+    spf_request = NULL;
+    return 0;
   }
 
-  if (SPF_set_helo_dom(spfcid, spf_helo_domain)) {
+  if (SPF_request_set_helo_dom(spf_request, spf_helo_domain)) {
     debug_printf("spf: SPF_set_helo_dom() failed.\n");
-    spfcid = NULL;
-    spfdcid_resolv = NULL;
-         return 0;
+    spf_server = NULL;
+    spf_request = NULL;
+    return 0;
   }
 
   return 1;
@@ -76,31 +61,30 @@ int spf_process(uschar **listptr, uschar *spf_envelope_sender) {
   uschar *list = *listptr;
   uschar *spf_result_id;
   uschar spf_result_id_buffer[128];
-  SPF_output_t spf_output;
-  int rc = SPF_RESULT_ERROR;
+  int rc = SPF_RESULT_PERMERROR;
 
-  if (!(spfcid && spfdcid)) {
+  if (!(spf_server && spf_request)) {
     /* no global context, assume temp error and skip to evaluation */
-    rc = SPF_RESULT_ERROR;
+    rc = SPF_RESULT_PERMERROR;
     goto SPF_EVALUATE;
   };
 
-  if (SPF_set_env_from(spfcid, spf_envelope_sender)) {
+  if (SPF_request_set_env_from(spf_request, spf_envelope_sender)) {
     /* Invalid sender address. This should be a real rare occurence */
-    rc = SPF_RESULT_ERROR;
+    rc = SPF_RESULT_PERMERROR;
     goto SPF_EVALUATE;
   }
 
   /* get SPF result */
-  spf_output = SPF_result(spfcid, spfdcid);
+  SPF_request_query_mailfrom(spf_request, &spf_response);
 
   /* set up expansion items */
-  spf_header_comment     = spf_output.header_comment ? (uschar *)spf_output.header_comment : NULL;
-  spf_received           = spf_output.received_spf ? (uschar *)spf_output.received_spf : NULL;
-  spf_result             = (uschar *)SPF_strresult(spf_output.result);
-  spf_smtp_comment       = spf_output.smtp_comment ? (uschar *)spf_output.smtp_comment : NULL;
+  spf_header_comment     = (uschar *)SPF_response_get_header_comment(spf_response);
+  spf_received           = (uschar *)SPF_response_get_received_spf(spf_response);
+  spf_result             = (uschar *)SPF_strresult(SPF_response_result(spf_response));
+  spf_smtp_comment       = (uschar *)SPF_response_get_smtp_comment(spf_response);
 
-  rc = spf_output.result;
+  rc = SPF_response_result(spf_response);
 
   /* We got a result. Now see if we should return OK or FAIL for it */
   SPF_EVALUATE:
index 5ff251b6d440b5f5b4bb51197d0e56c665c0b189..30583f44066d2fd6137ec0331498d71a11934fbf 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/spf.h,v 1.3 2005/02/17 11:58:26 ph10 Exp $ */
+/* $Cambridge: exim/src/src/spf.h,v 1.4 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
 
 #ifdef EXPERIMENTAL_SPF
 
+/* Yes, we do have ns_type. spf.h redefines it if we don't set this. Doh */
+#define HAVE_NS_TYPE
 #include <spf2/spf.h>
+
+
 #include <spf2/spf_dns_resolv.h>
 #include <spf2/spf_dns_cache.h>
 
+
 typedef struct spf_result_id {
   uschar *name;
   int    value;
index 5cdc9d3a75cead1862887ed773d64c0bb6e37b69..d787c5767376c6e20e3a1b6d7258312c52fc8ba7 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/spool_mbox.c,v 1.4 2005/02/17 11:58:26 ph10 Exp $ */
+/* $Cambridge: exim/src/src/spool_mbox.c,v 1.5 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -150,23 +150,23 @@ void unspool_mbox(void) {
 
       snprintf(CS mbox_path, 1024, "%s/scan/%s", spool_directory, spooled_message_id);
 
-       tempdir = opendir(CS mbox_path);
-       /* loop thru dir & delete entries */
-       n = 0;
-       do {
-         entry = readdir(tempdir);
-         if (entry == NULL) break;
-         snprintf(CS file_path, 1024,"%s/scan/%s/%s", spool_directory, spooled_message_id, entry->d_name);
-         if ( (Ustrcmp(entry->d_name,"..") != 0) && (Ustrcmp(entry->d_name,".") != 0) ) {
-           debug_printf("unspool_mbox(): unlinking '%s'\n", file_path);
+  tempdir = opendir(CS mbox_path);
+  /* loop thru dir & delete entries */
+  n = 0;
+  do {
+    entry = readdir(tempdir);
+    if (entry == NULL) break;
+    snprintf(CS file_path, 1024,"%s/scan/%s/%s", spool_directory, spooled_message_id, entry->d_name);
+    if ( (Ustrcmp(entry->d_name,"..") != 0) && (Ustrcmp(entry->d_name,".") != 0) ) {
+      debug_printf("unspool_mbox(): unlinking '%s'\n", file_path);
               n = unlink(CS file_path);
             };
-       } while (n > -1);
+  } while (n > -1);
 
-       closedir(tempdir);
+  closedir(tempdir);
 
-       /* remove directory */
-       n = rmdir(CS mbox_path);
+  /* remove directory */
+  n = rmdir(CS mbox_path);
     };
   };
 }
index 1b6d15d0533ba9871135c4846e1dfae42cdb6c7e..6d49a6d271e44bb84d9bd60ee2a2d551545fe06e 100644 (file)
@@ -1,11 +1,14 @@
-/* $Cambridge: exim/src/src/srs.c,v 1.4 2005/02/17 11:58:26 ph10 Exp $ */
+/* $Cambridge: exim/src/src/srs.c,v 1.5 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
 *************************************************/
 
 /* SRS - Sender rewriting scheme support
-  ©2004 Miles Wilton <miles@mirtol.com>
+  (C)2004 Miles Wilton <miles@mirtol.com>
+
+  SRS Support Version: 1.0a
+
   License: GPL */
 
 #include "exim.h"
@@ -24,72 +27,87 @@ uschar   *srs_db_reverse        = NULL;
 
 int eximsrs_init()
 {
-  int co;
   uschar *list = srs_config;
-  char secret_buf[SRS_MAX_SECRET_LENGTH];
-  char *secret;
-  char sbuf[4];
-  char *sbufp;
-  int hashlen, maxage;
+  uschar secret_buf[SRS_MAX_SECRET_LENGTH];
+  uschar *secret;
+  uschar sbuf[4];
+  uschar *sbufp;
 
-
-  if(!srs)
+  // Check if this instance of Exim has not initialized SRS
+  if(srs == NULL)
   {
-    /* Check config */
-    if(!srs_config)
+    int co = 0;
+    int hashlen, maxage;
+    BOOL usetimestamp, usehash;
+
+    /* Copy config vars */
+    hashlen = srs_hashlength;
+    maxage = srs_maxage;
+    usetimestamp = srs_usetimestamp;
+    usehash = srs_usehash;
+
+    /* Pass srs_config var (overrides new config vars) */
+    co = 0;
+    if(srs_config != NULL)
     {
-      log_write(0, LOG_MAIN | LOG_PANIC,
-          "SRS Configuration Error");
-      return DEFER;
+      secret = string_nextinlist(&list, &co, secret_buf, SRS_MAX_SECRET_LENGTH);
+
+      if((sbufp = string_nextinlist(&list, &co, sbuf, sizeof(sbuf))) != NULL)
+        maxage = atoi(sbuf);
+
+      if((sbufp = string_nextinlist(&list, &co, sbuf, sizeof(sbuf))) != NULL)
+        hashlen = atoi(sbuf);
+
+      if((sbufp = string_nextinlist(&list, &co, sbuf, sizeof(sbuf))) != NULL)
+        usetimestamp = atoi(sbuf);
+
+      if((sbufp = string_nextinlist(&list, &co, sbuf, sizeof(sbuf))) != NULL)
+        usehash = atoi(sbuf);
     }
 
-    /* Get config */
+    if(srs_hashmin == -1)
+      srs_hashmin = hashlen;
+
+    /* First secret specified in secrets? */
     co = 0;
-    if((secret = string_nextinlist(&list, &co, secret_buf,
-                                   SRS_MAX_SECRET_LENGTH)) == NULL)
+    list = srs_secrets;
+    if(secret == NULL)
     {
-      log_write(0, LOG_MAIN | LOG_PANIC,
-          "SRS Configuration Error: No secret specified");
-      return DEFER;
+      if((secret = string_nextinlist(&list, &co, secret_buf, SRS_MAX_SECRET_LENGTH)) == NULL)
+      {
+        log_write(0, LOG_MAIN | LOG_PANIC,
+            "SRS Configuration Error: No secret specified");
+        return DEFER;
+      }
     }
 
-    if((sbufp = string_nextinlist(&list, &co, sbuf, sizeof(sbuf))) == NULL)
-      maxage = 31;
-    else
-      maxage = atoi(sbuf);
+    /* Check config */
     if(maxage < 0 || maxage > 365)
     {
       log_write(0, LOG_MAIN | LOG_PANIC,
           "SRS Configuration Error: Invalid maximum timestamp age");
       return DEFER;
     }
-
-    if((sbufp = string_nextinlist(&list, &co, sbuf, sizeof(sbuf))) == NULL)
-      hashlen = 6;
-    else
-      hashlen = atoi(sbuf);
-    if(hashlen < 1 || hashlen > 20)
+    if(hashlen < 1 || hashlen > 20 || srs_hashmin < 1 || srs_hashmin > 20)
     {
       log_write(0, LOG_MAIN | LOG_PANIC,
           "SRS Configuration Error: Invalid hash length");
       return DEFER;
     }
 
-
-    if((srs = srs_open(secret, strnlen(secret, SRS_MAX_SECRET_LENGTH),
-                      maxage, hashlen, hashlen)) == NULL)
+    if((srs = srs_open(secret, Ustrlen(secret), maxage, hashlen, srs_hashmin)) == NULL)
     {
       log_write(0, LOG_MAIN | LOG_PANIC,
           "Failed to allocate SRS memory");
       return DEFER;
     }
 
+    srs_set_option(srs, SRS_OPTION_USETIMESTAMP, usetimestamp);
+    srs_set_option(srs, SRS_OPTION_USEHASH, usehash);
 
-    if((sbufp = string_nextinlist(&list, &co, sbuf, sizeof(sbuf))) != NULL)
-      srs_set_option(srs, SRS_OPTION_USETIMESTAMP, atoi(sbuf));
-
-    if((sbufp = string_nextinlist(&list, &co, sbuf, sizeof(sbuf))) != NULL)
-      srs_set_option(srs, SRS_OPTION_USEHASH, atoi(sbuf));
+    /* Extra secrets? */
+    while((secret = string_nextinlist(&list, &co, secret_buf, SRS_MAX_SECRET_LENGTH)) != NULL)
+        srs_add_secret(srs, secret, strnlen(secret, SRS_MAX_SECRET_LENGTH));
 
     DEBUG(D_any)
       debug_printf("SRS initialized\n");
@@ -101,7 +119,7 @@ int eximsrs_init()
 
 int eximsrs_done()
 {
-  if(srs)
+  if(srs != NULL)
     srs_close(srs);
 
   srs = NULL;
@@ -151,11 +169,12 @@ int eximsrs_reverse(uschar **result, uschar *address)
 int eximsrs_db_set(BOOL reverse, uschar *srs_db)
 {
   if(reverse)
-    srs_db_reverse = string_copy(srs_db);
+    srs_db_reverse = (srs_db == NULL ? NULL : string_copy(srs_db));
   else
-    srs_db_forward = string_copy(srs_db);
+    srs_db_forward = (srs_db == NULL ? NULL : string_copy(srs_db));
 
-  if(srs_set_db_functions(srs, eximsrs_db_insert, eximsrs_db_lookup) * SRS_RESULT_FAIL)
+  if(srs_set_db_functions(srs, (srs_db_forward ? eximsrs_db_insert : NULL),
+                               (srs_db_reverse ? eximsrs_db_lookup : NULL)) & SRS_RESULT_FAIL)
     return DEFER;
 
   return OK;
@@ -165,11 +184,14 @@ int eximsrs_db_set(BOOL reverse, uschar *srs_db)
 srs_result eximsrs_db_insert(srs_t *srs, char *data, uint data_len, char *result, uint result_len)
 {
   uschar *res;
-  char buf[64];
+  uschar buf[64];
+
+  if(srs_db_forward == NULL)
+    return SRS_RESULT_DBERROR;
 
   srs_db_address = string_copyn(data, data_len);
   if(srs_generate_unique_id(srs, srs_db_address, buf, 64) & SRS_RESULT_FAIL)
-    return DEFER;
+    return SRS_RESULT_DBERROR;
 
   srs_db_key = string_copyn(buf, 16);
 
@@ -179,7 +201,7 @@ srs_result eximsrs_db_insert(srs_t *srs, char *data, uint data_len, char *result
   if(result_len < 17)
     return SRS_RESULT_DBERROR;
 
-  strncpy(result, srs_db_key, result_len);
+  Ustrncpy(result, srs_db_key, result_len);
 
   return SRS_RESULT_OK;
 }
@@ -189,6 +211,9 @@ srs_result eximsrs_db_lookup(srs_t *srs, char *data, uint data_len, char *result
 {
   uschar *res;
 
+  if(srs_db_reverse == NULL)
+    return SRS_RESULT_DBERROR;
+
   srs_db_key = string_copyn(data, data_len);
   if((res = expand_string(srs_db_reverse)) == NULL)
     return SRS_RESULT_DBERROR;
index 645dfc25cf25b91f2fb888238a5e5253baeb1ae2..8243788718e7fc72e6e1c3cdf467fd77073283d4 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/structs.h,v 1.5 2005/04/28 13:06:32 ph10 Exp $ */
+/* $Cambridge: exim/src/src/structs.h,v 1.6 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -469,6 +469,10 @@ typedef struct address_item_propagated {
   uschar *errors_address;         /* where to send errors (NULL => sender) */
   header_line *extra_headers;     /* additional headers */
   uschar *remove_headers;         /* list of those to remove */
+
+  #ifdef EXPERIMENTAL_SRS
+  uschar *srs_sender;             /* Change return path when delivering */
+  #endif
 } address_item_propagated;
 
 /* Bits for the flags field below */
index 75e3ce7c6fa71f7ed6c83704d6f400c258a03f30..abdb5facc5c5dd8d5d5eade11b1ca58b06db6fb3 100644 (file)
@@ -1,4 +1,4 @@
-/* $Cambridge: exim/src/src/verify.c,v 1.16 2005/04/06 16:26:42 ph10 Exp $ */
+/* $Cambridge: exim/src/src/verify.c,v 1.17 2005/05/24 08:15:02 tom Exp $ */
 
 /*************************************************
 *     Exim - an Internet mail transport agent    *
@@ -1229,6 +1229,10 @@ else for (addr_list = addr_local, i = 0; i < 2; addr_list = addr_remote, i++)
     addr_list = addr->next;
 
     fprintf(f, "%s", CS addr->address);
+#ifdef EXPERIMENTAL_SRS
+    if(addr->p.srs_sender)
+      fprintf(f, "    [srs = %s]", addr->p.srs_sender);
+#endif
     while (p != NULL)
       {
       fprintf(f, "\n    <-- %s", p->address);