]> source.dussan.org Git - rspamd.git/commitdiff
[Feature] Use new received parser instead of old one
authorVsevolod Stakhov <vsevolod@highsecure.ru>
Tue, 14 Jun 2016 17:07:27 +0000 (18:07 +0100)
committerVsevolod Stakhov <vsevolod@highsecure.ru>
Tue, 14 Jun 2016 17:07:27 +0000 (18:07 +0100)
src/libmime/message.c
src/libmime/parsers/smtp_received_parser.c
src/lua/lua_task.c
src/ragel/smtp_ip.rl
src/ragel/smtp_received_parser.rl

index e8f5cd96bece36cee7daa337e223fd2ab641dece..6206c9e7f64658a19248d602fdea266611a25bea 100644 (file)
@@ -51,338 +51,6 @@ rspamd_message_quark (void)
        return g_quark_from_static_string ("mime-error");
 }
 
-static void
-parse_qmail_recv (rspamd_mempool_t * pool,
-       gchar *line,
-       struct received_header *r)
-{
-       gchar *s, *p, t;
-
-       /* We are interested only with received from network headers */
-       if ((p = strstr (line, "from network")) == NULL) {
-               r->is_error = 2;
-               return;
-       }
-
-       p += sizeof ("from network") - 1;
-       while (g_ascii_isspace (*p) || *p == '[') {
-               p++;
-       }
-       /* format is ip/host */
-       s = p;
-       if (*p) {
-               while (g_ascii_isdigit (*++p) || *p == '.') ;
-               if (*p != '/') {
-                       r->is_error = 1;
-                       return;
-               }
-               else {
-                       *p = '\0';
-                       r->real_ip = rspamd_mempool_strdup (pool, s);
-                       *p = '/';
-                       /* Now try to parse hostname */
-                       s = ++p;
-                       while (g_ascii_isalnum (*p) || *p == '.' || *p == '-' || *p ==
-                               '_') {
-                               p++;
-                       }
-                       t = *p;
-                       *p = '\0';
-                       r->real_hostname = rspamd_mempool_strdup (pool, s);
-                       *p = t;
-               }
-       }
-}
-
-static void
-parse_recv_header (rspamd_mempool_t * pool,
-       struct raw_header *rh,
-       struct received_header *r)
-{
-       gchar *p, *s, t, **res = NULL;
-       gchar *line;
-       enum {
-               RSPAMD_RECV_STATE_INIT = 0,
-               RSPAMD_RECV_STATE_FROM,
-               RSPAMD_RECV_STATE_IP_BLOCK,
-               RSPAMD_RECV_STATE_BRACES_BLOCK,
-               RSPAMD_RECV_STATE_BY_BLOCK,
-               RSPAMD_RECV_STATE_PARSE_IP,
-               RSPAMD_RECV_STATE_PARSE_IP6,
-               RSPAMD_RECV_STATE_SKIP_SPACES,
-               RSPAMD_RECV_STATE_ERROR
-       } state = RSPAMD_RECV_STATE_INIT, next_state = RSPAMD_RECV_STATE_INIT;
-       gboolean is_exim = FALSE;
-
-       line = rh->decoded;
-       if (line == NULL) {
-               return;
-       }
-
-       g_strstrip (line);
-       p = line;
-       s = line;
-
-       while (*p) {
-               switch (state) {
-               /* Initial state, search for from */
-               case RSPAMD_RECV_STATE_INIT:
-                       if (*p == 'f' || *p == 'F') {
-                               if (g_ascii_tolower (*++p) == 'r' && g_ascii_tolower (*++p) ==
-                                       'o' && g_ascii_tolower (*++p) == 'm') {
-                                       p++;
-                                       state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                                       next_state = RSPAMD_RECV_STATE_FROM;
-                               }
-                       }
-                       else if (g_ascii_tolower (*p) == 'b' &&
-                               g_ascii_tolower (*(p + 1)) == 'y') {
-                               state = RSPAMD_RECV_STATE_IP_BLOCK;
-                       }
-                       else {
-                               /* This can be qmail header, parse it separately */
-                               parse_qmail_recv (pool, line, r);
-                               return;
-                       }
-                       break;
-               /* Read hostname */
-               case RSPAMD_RECV_STATE_FROM:
-                       if (*p == '[') {
-                               /* This should be IP address */
-                               res = &r->from_ip;
-                               state = RSPAMD_RECV_STATE_PARSE_IP;
-                               next_state = RSPAMD_RECV_STATE_IP_BLOCK;
-                               s = ++p;
-                       }
-                       else if (g_ascii_isalnum (*p) || *p == '.' || *p == '-' || *p ==
-                               '_') {
-                               p++;
-                       }
-                       else {
-                               t = *p;
-                               *p = '\0';
-                               r->from_hostname = rspamd_mempool_strdup (pool, s);
-                               *p = t;
-                               state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                               next_state = RSPAMD_RECV_STATE_IP_BLOCK;
-                       }
-                       break;
-               /* Try to extract additional info */
-               case RSPAMD_RECV_STATE_IP_BLOCK:
-                       /* Try to extract ip or () info or by */
-                       if (g_ascii_tolower (*p) == 'b' && g_ascii_tolower (*(p + 1)) ==
-                               'y') {
-                               p += 2;
-                               /* Skip spaces after by */
-                               state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                               next_state = RSPAMD_RECV_STATE_BY_BLOCK;
-                       }
-                       else if (*p == '(') {
-                               state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                               next_state = RSPAMD_RECV_STATE_BRACES_BLOCK;
-                               p++;
-                       }
-                       else if (*p == '[') {
-                               /* Got ip before '(' so extract it */
-                               s = ++p;
-                               res = &r->from_ip;
-                               state = RSPAMD_RECV_STATE_PARSE_IP;
-                               next_state = RSPAMD_RECV_STATE_IP_BLOCK;
-                       }
-                       else {
-                               p++;
-                       }
-                       break;
-               /* We are in () block. Here can be found real hostname and real ip, this is written by some MTA */
-               case RSPAMD_RECV_STATE_BRACES_BLOCK:
-                       /* End of block */
-                       if (g_ascii_isalnum (*p) || *p == '.' || *p == '-' ||
-                               *p == '_' || *p == ':') {
-                               p++;
-                       }
-                       else if (*p == '[') {
-                               s = ++p;
-                               state = RSPAMD_RECV_STATE_PARSE_IP;
-                               res = &r->real_ip;
-                               next_state = RSPAMD_RECV_STATE_BRACES_BLOCK;
-                       }
-                       else {
-                               if (p > s) {
-                                       /* Got some real hostname */
-                                       /* check whether it is helo or p is not space symbol */
-                                       if (!g_ascii_isspace (*p) || *(p + 1) != '[') {
-                                               /* Exim style ([ip]:port helo=hostname) */
-                                               if (*s == ':' && (g_ascii_isspace (*p) || *p == ')')) {
-                                                       /* Ip ending */
-                                                       is_exim = TRUE;
-                                                       state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                                                       next_state = RSPAMD_RECV_STATE_BRACES_BLOCK;
-                                               }
-                                               else if (p - s == 4 && memcmp (s, "helo=", 5) == 0) {
-                                                       p++;
-                                                       is_exim = TRUE;
-                                                       if (r->real_hostname == NULL && r->from_hostname !=
-                                                               NULL) {
-                                                               r->real_hostname = r->from_hostname;
-                                                       }
-                                                       s = p;
-                                                       while (*p != ')' && !g_ascii_isspace (*p) && *p !=
-                                                               '\0') {
-                                                               p++;
-                                                       }
-                                                       if (p > s) {
-                                                               r->from_hostname = rspamd_mempool_alloc (pool,
-                                                                               p - s + 1);
-                                                               rspamd_strlcpy (r->from_hostname, s, p - s + 1);
-                                                       }
-                                               }
-                                               else if (p - s == 4 && memcmp (s, "port=", 5) == 0) {
-                                                       p++;
-                                                       is_exim = TRUE;
-                                                       while (g_ascii_isdigit (*p)) {
-                                                               p++;
-                                                       }
-                                                       state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                                                       next_state = RSPAMD_RECV_STATE_BRACES_BLOCK;
-                                               }
-                                               else if (*p == '=' && is_exim) {
-                                                       /* Just skip unknown pairs */
-                                                       p++;
-                                                       while (!g_ascii_isspace (*p) && *p != ')' && *p !=
-                                                               '\0') {
-                                                               p++;
-                                                       }
-                                                       state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                                                       next_state = RSPAMD_RECV_STATE_BRACES_BLOCK;
-                                               }
-                                               else {
-                                                       /* skip all  */
-                                                       while (*p++ != ')' && *p != '\0') ;
-                                                       state = RSPAMD_RECV_STATE_IP_BLOCK;
-                                               }
-                                       }
-                                       else {
-                                               /* Postfix style (hostname [ip]) */
-                                               t = *p;
-                                               *p = '\0';
-                                               r->real_hostname = rspamd_mempool_strdup (pool, s);
-                                               *p = t;
-                                               /* Now parse ip */
-                                               p += 2;
-                                               s = p;
-                                               res = &r->real_ip;
-                                               state = RSPAMD_RECV_STATE_PARSE_IP;
-                                               next_state = RSPAMD_RECV_STATE_BRACES_BLOCK;
-                                               continue;
-                                       }
-                                       if (*p == ')') {
-                                               p++;
-                                               state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                                               next_state = RSPAMD_RECV_STATE_IP_BLOCK;
-                                       }
-                               }
-                               else if (*p == ')') {
-                                       p++;
-                                       state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                                       next_state = RSPAMD_RECV_STATE_IP_BLOCK;
-                               }
-                               else {
-                                       r->is_error = 1;
-                                       return;
-                               }
-                       }
-                       break;
-               /* Got by word */
-               case RSPAMD_RECV_STATE_BY_BLOCK:
-                       /* Here can be only hostname */
-                       if ((g_ascii_isalnum (*p) || *p == '.' || *p == '-'
-                               || *p == '_') && p[1] != '\0') {
-                               p++;
-                       }
-                       else {
-                               /* We got something like hostname */
-                               if (p[1] != '\0') {
-                                       t = *p;
-                                       *p = '\0';
-                                       r->by_hostname = rspamd_mempool_strdup (pool, s);
-                                       *p = t;
-                               }
-                               else {
-                                       r->by_hostname = rspamd_mempool_strdup (pool, s);
-                               }
-                               /* Now end of parsing */
-                               if (is_exim) {
-                                       /* Adjust for exim received */
-                                       if (r->real_ip == NULL && r->from_ip != NULL) {
-                                               r->real_ip = r->from_ip;
-                                       }
-                                       else if (r->from_ip == NULL && r->real_ip != NULL) {
-                                               r->from_ip = r->real_ip;
-                                               if (r->real_hostname == NULL && r->from_hostname !=
-                                                       NULL) {
-                                                       r->real_hostname = r->from_hostname;
-                                               }
-                                       }
-                               }
-                               return;
-                       }
-                       break;
-
-               /* Extract ip */
-               case RSPAMD_RECV_STATE_PARSE_IP:
-                       if (*p == 'I') {
-                               /* IPv6: */
-                               state = RSPAMD_RECV_STATE_PARSE_IP6;
-                       }
-                       else {
-                               while (g_ascii_isxdigit (*p) || *p == '.' || *p == ':') {
-                                       p++;
-                               }
-                               if (*p != ']') {
-                                       /* Not an ip in fact */
-                                       state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                                       p++;
-                               }
-                               else {
-                                       *p = '\0';
-                                       *res = rspamd_mempool_strdup (pool, s);
-                                       *p = ']';
-                                       p++;
-                                       state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                               }
-                       }
-                       break;
-               case RSPAMD_RECV_STATE_PARSE_IP6:
-                       if (g_ascii_strncasecmp (p, "IPv6:", sizeof ("IPv6") - 1) == 0) {
-                               p += sizeof ("IPv6") - 1;
-                               s = p;
-                               state = RSPAMD_RECV_STATE_PARSE_IP;
-                       }
-                       else {
-                               state = RSPAMD_RECV_STATE_SKIP_SPACES;
-                       }
-                       break;
-               /* Skip spaces */
-               case RSPAMD_RECV_STATE_SKIP_SPACES:
-                       if (!g_ascii_isspace (*p)) {
-                               state = next_state;
-                               s = p;
-                       }
-                       else {
-                               p++;
-                       }
-                       break;
-               default:
-                       r->is_error = 1;
-                       return;
-                       break;
-               }
-       }
-
-       r->is_error = 1;
-       return;
-}
-
 static void
 append_raw_header (struct rspamd_task *task,
                GHashTable *target, struct raw_header *rh)
@@ -1779,15 +1447,13 @@ rspamd_message_parse (struct rspamd_task *task)
        rspamd_images_process (task);
 
        /* Parse received headers */
-       first =
-                       rspamd_message_get_header (task, "Received", FALSE);
+       first = rspamd_message_get_header (task, "Received", FALSE);
 
        for (cur = first, i = 0; cur != NULL; cur = g_list_next (cur), i ++) {
-               recv =
-                               rspamd_mempool_alloc0 (task->task_pool,
-                                               sizeof (struct received_header));
-               parse_recv_header (task->task_pool, cur->data, recv);
-
+               recv = rspamd_mempool_alloc0 (task->task_pool,
+                               sizeof (struct received_header));
+               rh = cur->data;
+               rspamd_smtp_recieved_parse (task, rh->decoded, strlen (rh->decoded), recv);
                /*
                 * For the first header we must ensure that
                 * received is consistent with the IP that we obtain through
@@ -1795,22 +1461,19 @@ rspamd_message_parse (struct rspamd_task *task)
                 */
                if (i == 0) {
                        gboolean need_recv_correction = FALSE;
+                       rspamd_inet_addr_t *raddr = recv->addr;
 
                        if (recv->real_ip == NULL || (task->cfg && task->cfg->ignore_received)) {
                                need_recv_correction = TRUE;
                        }
                        else if (!(task->flags & RSPAMD_TASK_FLAG_NO_IP) && task->from_addr) {
-                               rspamd_inet_addr_t *raddr = NULL;
-
-                               if (!rspamd_parse_inet_address (&raddr, recv->real_ip, 0)) {
+                               if (raddr) {
                                        need_recv_correction = TRUE;
                                }
                                else {
                                        if (rspamd_inet_address_compare (raddr, task->from_addr) != 0) {
                                                need_recv_correction = TRUE;
                                        }
-
-                                       rspamd_inet_address_destroy (raddr);
                                }
 
                        }
@@ -1825,11 +1488,14 @@ rspamd_message_parse (struct rspamd_task *task)
                                trecv->real_ip = rspamd_mempool_strdup (task->task_pool,
                                                rspamd_inet_address_to_string (task->from_addr));
                                trecv->from_ip = trecv->real_ip;
+                               trecv->addr = task->from_addr;
 
                                if (task->hostname) {
                                        trecv->real_hostname = task->hostname;
                                        trecv->from_hostname = trecv->real_hostname;
                                }
+
+                               g_ptr_array_add (task->received, trecv);
                        }
                }
 
index ffdfde8b4c2d16cf19e8ca5831510d8cbe58470f..c945208fbfcb07c5c5690f7c19e0782a71b160c9 100644 (file)
@@ -1,7 +1,7 @@
 
 #line 1 "../rspamd/src/ragel/smtp_received_parser.rl"
 
-#line 201 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 237 "../rspamd/src/ragel/smtp_received_parser.rl"
 
 
 
@@ -6183,7 +6183,7 @@ static const int smtp_received_parser_error = 0;
 static const int smtp_received_parser_en_main = 1;
 
 
-#line 204 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 240 "../rspamd/src/ragel/smtp_received_parser.rl"
 
 static int
 rspamd_smtp_recieved_parse (struct rspamd_task *task, const char *data, size_t len, struct received_header *rh)
@@ -6195,7 +6195,7 @@ rspamd_smtp_recieved_parse (struct rspamd_task *task, const char *data, size_t l
               *reported_ip_start, *reported_ip_end,
               *ip_start, *ip_end;
   const char *p = data, *pe = data + len, *eof;
-  int cs;
+  int cs, in_v6 = 0;
 
   memset (rh, 0, sizeof (*rh));
   real_domain_start = NULL;
@@ -6220,7 +6220,7 @@ rspamd_smtp_recieved_parse (struct rspamd_task *task, const char *data, size_t l
        cs = smtp_received_parser_start;
        }
 
-#line 235 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 271 "../rspamd/src/ragel/smtp_received_parser.rl"
 
 #line 6226 "../rspamd/src/libmime/parsers/smtp_received_parser.c"
        {
@@ -6292,23 +6292,26 @@ _match:
        case 24:
 #line 6 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
+    in_v6 = 1;
     ip_start = p;
   }
        break;
        case 25:
-#line 12 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 14 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
-    ip_start = p;
+    if (!in_v6) {
+      ip_start = p;
+    }
   }
        break;
        case 9:
-#line 19 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 25 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->user = p;
   }
        break;
        case 11:
-#line 23 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 29 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->user) {
       addr->user_len = p - addr->user;
@@ -6316,20 +6319,20 @@ _match:
   }
        break;
        case 17:
-#line 29 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 35 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->domain = p;
   }
        break;
        case 19:
-#line 39 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 45 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->domain = p;
     addr->flags |= RSPAMD_EMAIL_ADDR_IP;
   }
        break;
        case 21:
-#line 44 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 50 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->domain) {
       addr->domain_len = p - addr->domain;
@@ -6337,25 +6340,25 @@ _match:
   }
        break;
        case 13:
-#line 50 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 56 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->flags |= RSPAMD_EMAIL_ADDR_HAS_BACKSLASH;
   }
        break;
        case 12:
-#line 54 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 60 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->flags |= RSPAMD_EMAIL_ADDR_QUOTED;
   }
        break;
        case 16:
-#line 73 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 79 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->addr = p;
   }
        break;
        case 30:
-#line 77 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->addr) {
       addr->addr_len = p - addr->addr;
@@ -6363,37 +6366,57 @@ _match:
   }
        break;
        case 4:
-#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 89 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = p;
   }
        break;
        case 36:
-#line 86 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 92 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_end = p;
   }
        break;
        case 5:
-#line 96 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 102 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
-    real_domain_start = p;
+    real_ip_start = p;
   }
        break;
        case 37:
-#line 99 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 105 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
-    real_domain_end = p;
+    if (ip_start && ip_end && ip_end > ip_start) {
+      real_ip_start = ip_start;
+      real_ip_end = ip_end;
+    }
+    else {
+      real_ip_end = p;
+    }
+
+    ip_start = NULL;
+    ip_end = NULL;
   }
        break;
        case 38:
-#line 135 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 160 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
-    /* Do nothing here for now */
+    guint len;
+
+    if (real_domain_end && real_domain_start && real_domain_end > real_domain_start) {
+      len = real_domain_end - real_domain_start;
+      rh->by_hostname = rspamd_mempool_alloc (task->task_pool, len + 1);
+      rspamd_strlcpy (rh->by_hostname, real_domain_start, len + 1);
+    }
+    else if (reported_domain_end && reported_domain_start && reported_domain_end > reported_domain_start) {
+      len = reported_domain_end - reported_domain_start;
+      rh->by_hostname = rspamd_mempool_alloc (task->task_pool, len + 1);
+      rspamd_strlcpy (rh->by_hostname, reported_domain_start, len + 1);
+    }
   }
        break;
        case 39:
-#line 139 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 175 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     guint len;
 
@@ -6425,49 +6448,50 @@ _match:
       rh->from_hostname = rh->real_hostname;
     }
 
-    if (rh->real_ip && ip_start && ip_end && ip_end > ip_start) {
-      if (rspamd_parse_inet_address (&rh->addr, ip_start, ip_end - ip_start)) {
+    if (rh->real_ip) {
+      if (rspamd_parse_inet_address (&rh->addr, rh->real_ip, strlen (rh->real_ip))) {
         rspamd_mempool_add_destructor (task->task_pool, (rspamd_mempool_destruct_t)rspamd_inet_address_destroy, rh->addr);
       }
     }
   }
        break;
        case 35:
-#line 181 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 217 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     rh->type = RSPAMD_RECEIVED_SMTP;
   }
        break;
        case 32:
-#line 184 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 220 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     rh->type = RSPAMD_RECEIVED_ESMTPS;
   }
        break;
        case 31:
-#line 187 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 223 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     rh->type = RSPAMD_RECEIVED_ESMTP;
   }
        break;
        case 34:
-#line 190 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 226 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     rh->type = RSPAMD_RECEIVED_LMTP;
   }
        break;
        case 33:
-#line 193 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 229 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     rh->type = RSPAMD_RECEIVED_IMAP;
   }
        break;
        case 27:
-#line 9 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 10 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
+    in_v6 = 0;
     ip_end = p;
   }
-#line 44 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 50 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->domain) {
       addr->domain_len = p - addr->domain;
@@ -6475,11 +6499,13 @@ _match:
   }
        break;
        case 23:
-#line 15 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 19 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
-    ip_end = p;
+    if (!in_v6) {
+      ip_end = p;
+    }
   }
-#line 44 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 50 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->domain) {
       addr->domain_len = p - addr->domain;
@@ -6487,11 +6513,11 @@ _match:
   }
        break;
        case 10:
-#line 19 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 25 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->user = p;
   }
-#line 23 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 29 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->user) {
       addr->user_len = p - addr->user;
@@ -6499,13 +6525,13 @@ _match:
   }
        break;
        case 28:
-#line 33 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 39 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->domain) {
       addr->domain_len = p - addr->domain;
     }
   }
-#line 77 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->addr) {
       addr->addr_len = p - addr->addr;
@@ -6513,22 +6539,24 @@ _match:
   }
        break;
        case 20:
-#line 39 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 45 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->domain = p;
     addr->flags |= RSPAMD_EMAIL_ADDR_IP;
   }
-#line 12 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 14 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
-    ip_start = p;
+    if (!in_v6) {
+      ip_start = p;
+    }
   }
        break;
        case 14:
-#line 50 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 56 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->flags |= RSPAMD_EMAIL_ADDR_HAS_BACKSLASH;
   }
-#line 23 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 29 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->user) {
       addr->user_len = p - addr->user;
@@ -6536,39 +6564,39 @@ _match:
   }
        break;
        case 29:
-#line 69 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 75 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->flags |= RSPAMD_EMAIL_ADDR_BRACED;
   }
-#line 177 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 213 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
 
   }
        break;
        case 15:
-#line 73 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 79 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->addr = p;
   }
-#line 19 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 25 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     addr->user = p;
   }
        break;
        case 22:
-#line 77 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->addr) {
       addr->addr_len = p - addr->addr;
     }
   }
-#line 177 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 213 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
 
   }
        break;
        case 2:
-#line 109 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 134 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = NULL;
     real_domain_end = NULL;
@@ -6581,13 +6609,13 @@ _match:
     ip_start = NULL;
     ip_end = NULL;
   }
-#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 89 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = p;
   }
        break;
        case 7:
-#line 122 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 147 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = NULL;
     real_domain_end = NULL;
@@ -6600,21 +6628,24 @@ _match:
     ip_start = NULL;
     ip_end = NULL;
   }
-#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 89 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = p;
   }
        break;
        case 26:
-#line 15 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 19 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
-    ip_end = p;
+    if (!in_v6) {
+      ip_end = p;
+    }
   }
-#line 9 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 10 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
+    in_v6 = 0;
     ip_end = p;
   }
-#line 44 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 50 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->domain) {
       addr->domain_len = p - addr->domain;
@@ -6622,47 +6653,58 @@ _match:
   }
        break;
        case 18:
-#line 33 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 39 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->domain) {
       addr->domain_len = p - addr->domain;
     }
   }
-#line 77 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     if (addr->addr) {
       addr->addr_len = p - addr->addr;
     }
   }
-#line 177 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 213 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
 
   }
        break;
        case 8:
-#line 86 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 92 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_end = p;
   }
-#line 92 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 98 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     reported_domain_end = p;
   }
-#line 135 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 160 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
-    /* Do nothing here for now */
+    guint len;
+
+    if (real_domain_end && real_domain_start && real_domain_end > real_domain_start) {
+      len = real_domain_end - real_domain_start;
+      rh->by_hostname = rspamd_mempool_alloc (task->task_pool, len + 1);
+      rspamd_strlcpy (rh->by_hostname, real_domain_start, len + 1);
+    }
+    else if (reported_domain_end && reported_domain_start && reported_domain_end > reported_domain_start) {
+      len = reported_domain_end - reported_domain_start;
+      rh->by_hostname = rspamd_mempool_alloc (task->task_pool, len + 1);
+      rspamd_strlcpy (rh->by_hostname, reported_domain_start, len + 1);
+    }
   }
        break;
        case 3:
-#line 86 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 92 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_end = p;
   }
-#line 92 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 98 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     reported_domain_end = p;
   }
-#line 139 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 175 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     guint len;
 
@@ -6694,15 +6736,15 @@ _match:
       rh->from_hostname = rh->real_hostname;
     }
 
-    if (rh->real_ip && ip_start && ip_end && ip_end > ip_start) {
-      if (rspamd_parse_inet_address (&rh->addr, ip_start, ip_end - ip_start)) {
+    if (rh->real_ip) {
+      if (rspamd_parse_inet_address (&rh->addr, rh->real_ip, strlen (rh->real_ip))) {
         rspamd_mempool_add_destructor (task->task_pool, (rspamd_mempool_destruct_t)rspamd_inet_address_destroy, rh->addr);
       }
     }
   }
        break;
        case 1:
-#line 109 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 134 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = NULL;
     real_domain_end = NULL;
@@ -6715,17 +6757,17 @@ _match:
     ip_start = NULL;
     ip_end = NULL;
   }
-#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 89 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = p;
   }
-#line 89 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 95 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     reported_domain_start = p;
   }
        break;
        case 6:
-#line 122 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 147 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = NULL;
     real_domain_end = NULL;
@@ -6738,16 +6780,16 @@ _match:
     ip_start = NULL;
     ip_end = NULL;
   }
-#line 83 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 89 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     real_domain_start = p;
   }
-#line 89 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 95 "../rspamd/src/ragel/smtp_received_parser.rl"
        {
     reported_domain_start = p;
   }
        break;
-#line 6751 "../rspamd/src/libmime/parsers/smtp_received_parser.c"
+#line 6793 "../rspamd/src/libmime/parsers/smtp_received_parser.c"
        }
 
 _again:
@@ -6759,7 +6801,7 @@ _again:
        _out: {}
        }
 
-#line 236 "../rspamd/src/ragel/smtp_received_parser.rl"
+#line 272 "../rspamd/src/ragel/smtp_received_parser.rl"
 
   return cs;
 }
index 7a756679b317dd9f44bd31aed90332309176509c..cbcaf2ed501b247bc8fc9a1a41529b8cebabf33d 100644 (file)
@@ -1427,6 +1427,7 @@ lua_task_get_received_headers (lua_State * L)
 {
        struct rspamd_task *task = lua_check_task (L, 1);
        struct received_header *rh;
+       const gchar *proto;
        guint i, k = 1;
 
        if (task) {
@@ -1445,12 +1446,35 @@ lua_task_get_received_headers (lua_State * L)
 
                        lua_newtable (L);
                        rspamd_lua_table_set (L, "from_hostname", rh->from_hostname);
-                       lua_pushstring (L, "from_ip");
-                       rspamd_lua_ip_push_fromstring (L, rh->from_ip);
-                       lua_settable (L, -3);
+                       rspamd_lua_table_set (L, "from_ip", rh->from_ip);
                        rspamd_lua_table_set (L, "real_hostname", rh->real_hostname);
                        lua_pushstring (L, "real_ip");
-                       rspamd_lua_ip_push_fromstring (L, rh->real_ip);
+                       rspamd_lua_ip_push (L, rh->addr);
+                       lua_settable (L, -3);
+                       lua_pushstring (L, "proto");
+
+                       switch (rh->type) {
+                       case RSPAMD_RECEIVED_SMTP:
+                               proto = "smtp";
+                               break;
+                       case RSPAMD_RECEIVED_ESMTP:
+                               proto = "esmtp";
+                               break;
+                       case RSPAMD_RECEIVED_ESMTPS:
+                               proto = "esmtps";
+                               break;
+                       case RSPAMD_RECEIVED_LMTP:
+                               proto = "lmtp";
+                               break;
+                       case RSPAMD_RECEIVED_IMAP:
+                               proto = "imap";
+                               break;
+                       case RSPAMD_RECEIVED_UNKNOWN:
+                       default:
+                               proto = "unknown";
+                               break;
+                       }
+                       lua_pushstring (L, proto);
                        lua_settable (L, -3);
                        rspamd_lua_table_set (L, "by_hostname", rh->by_hostname);
                        lua_rawseti (L, -2, k ++);
index b060b750afe783ed2e09e0640e0cb26e18ff8b9f..dae90a09651cdb1d7216d48c62e35e98ed4dc7c2 100644 (file)
@@ -15,5 +15,5 @@
                   (IPv6_hex (":" IPv6_hex){0,3} ":")?
                   IPv4_address_literal;
   IPv6_addr      = IPv6_full | IPv6_comp | IPv6v4_full | IPv6v4_comp;
-  IPv6_address_literal  = "IPv6:" (IPv6_addr >IP6_start %IP6_end);
+  IPv6_address_literal  = "IPv6:" %IP6_start IPv6_addr %IP6_end;
 }%%
\ No newline at end of file
index 6cc054a4d39dc15eb4d5d4befcdba03eaeacdff0..339326900399bdae48fd5d173cba809bda153dfb 100644 (file)
@@ -4,16 +4,22 @@
 
 
   action IP6_start {
+    in_v6 = 1;
     ip_start = p;
   }
   action IP6_end {
+    in_v6 = 0;
     ip_end = p;
   }
   action IP4_start {
-    ip_start = p;
+    if (!in_v6) {
+      ip_start = p;
+    }
   }
   action IP4_end {
-    ip_end = p;
+    if (!in_v6) {
+      ip_end = p;
+    }
   }
 
   action User_start {
   }
 
   action Real_IP_Start {
-    real_domain_start = p;
+    real_ip_start = p;
   }
   action Real_IP_End {
-    real_domain_end = p;
+    if (ip_start && ip_end && ip_end > ip_start) {
+      real_ip_start = ip_start;
+      real_ip_end = ip_end;
+    }
+    else {
+      real_ip_end = p;
+    }
+
+    ip_start = NULL;
+    ip_end = NULL;
   }
   action Reported_IP_Start {
-    reported_domain_start = p;
+    reported_ip_start = p;
   }
   action Reported_IP_End {
-    reported_domain_end = p;
+
+    if (ip_start && ip_end && ip_end > ip_start) {
+      reported_ip_start = ip_start;
+      reported_ip_end = ip_end;
+    }
+    else {
+      reported_ip_end = p;
+    }
+
+    ip_start = NULL;
+    ip_end = NULL;
   }
 
   action From_Start {
   }
 
   action By_End {
-    /* Do nothing here for now */
+    guint len;
+
+    if (real_domain_end && real_domain_start && real_domain_end > real_domain_start) {
+      len = real_domain_end - real_domain_start;
+      rh->by_hostname = rspamd_mempool_alloc (task->task_pool, len + 1);
+      rspamd_strlcpy (rh->by_hostname, real_domain_start, len + 1);
+    }
+    else if (reported_domain_end && reported_domain_start && reported_domain_end > reported_domain_start) {
+      len = reported_domain_end - reported_domain_start;
+      rh->by_hostname = rspamd_mempool_alloc (task->task_pool, len + 1);
+      rspamd_strlcpy (rh->by_hostname, reported_domain_start, len + 1);
+    }
   }
 
   action From_End {
       rh->from_hostname = rh->real_hostname;
     }
 
-    if (rh->real_ip && ip_start && ip_end && ip_end > ip_start) {
-      if (rspamd_parse_inet_address (&rh->addr, ip_start, ip_end - ip_start)) {
+    if (rh->real_ip) {
+      if (rspamd_parse_inet_address (&rh->addr, rh->real_ip, strlen (rh->real_ip))) {
         rspamd_mempool_add_destructor (task->task_pool, (rspamd_mempool_destruct_t)rspamd_inet_address_destroy, rh->addr);
       }
     }
@@ -212,7 +248,7 @@ rspamd_smtp_recieved_parse (struct rspamd_task *task, const char *data, size_t l
               *reported_ip_start, *reported_ip_end,
               *ip_start, *ip_end;
   const char *p = data, *pe = data + len, *eof;
-  int cs;
+  int cs, in_v6 = 0;
 
   memset (rh, 0, sizeof (*rh));
   real_domain_start = NULL;