# Copyright (c) 2010 Flowerfire, Inc. All Rights Reserved. exim_4 = { plugin_version = "1.1.1" info.1.manfacturer = "Exim" info.1.device = "Internet Mailer 4" info.1.version.1 = "" # 2007-09-11 - 1.0 - KBB - Added version number and changed file name from beta_exim_4.cfg # 2008-06-30 - 1.1 - KBB - Added support for new format by discarding section # like this: [ID 197553 mail.info]. Also set name for P= pair to protocol. # 2010-11-04 - 1.0.1 - MSG - Edited info lines. # The name of the log format log.format.format_label = "Exim 4 Log Format" log.miscellaneous.log_data_type = "syslog_required" log.miscellaneous.log_format_type = "mail_server" # The log is in this format if any of the first ten lines match this regular expression log.format.autodetect_regular_expression = "[0-9][0-9][0-9][0-9]-[0-9][0-9]-[0-9][0-9] [0-9][0-9]:[0-9][0-9]:[0-9][0-9] [0-9a-zA-Z-]+ (<=|=>|->|\\*>|\\*\\*|==)" # The format of dates and times in this log # log.format.date_format = "yyyy-mm-dd" # log.format.time_format = "hh:mm:ss" # All log field parsing will be done using the parsing filters log.format.parse_only_with_filters = "true" # Log fields log.fields = { sender = { type = "hierarchical" hierarchy_dividers = "@" left_to_right = false leading_divider = false } # sender recipient = { type = "hierarchical" hierarchy_dividers = "@" left_to_right = false leading_divider = false } # recipient recipient_username = "" subject = "" protocol = "" transport_name = "" source_hostname = "" source_ip.type = "host" message_id = "" size = "" router_name = "" authenticated_name = "" smtp_delivery_conf = "" cert_verif_status = "" dist_name_from_peer = "" shadow_transport_name = "" user_rfc1413 = "" tls_cipher_suite = "" antibody_filter = "" messages_filtered = "" } # log.fields # Log Parsing Filters log.parsing_filters.parse = ` v.name_value_pairs = ""; # Trim off leading "(none)" # e.g. 2008:01:31-00:00:08 (none) exim[12573]: 2008-01-31 00:00:08 unexpected disconnection while reading SMTP command from ([5.201.28.13]) [5.201.28.11] if (matches_regular_expression(v.syslog_message, '^[(][^)]+[)] (.*)$')) then v.syslog_message = $1; # Trim off leading daemon[pid] if (matches_regular_expression(v.syslog_message, '^[^] :]*\\\\[[0-9]+\\\\]: (.*)$')) then v.syslog_message = $1; # Discard Antibody [1\40] header if (matches_regular_expression(v.syslog_message, '^\\\\[[0-9]+\\\\\\\\[0-9]+\\\\] (.*)$')) then v.syslog_message = $1; # Discard [ID...] section #May 22 03:10:03 mailer exim[15666]: [ID 197553 mail.info] 2008-05-22 03:10:03 no host name found for IP address 22.22.22.22 if (matches_regular_expression(v.syslog_message, '^\\\\[ID [^ ]+ [^]]+\\\\] (.*)$')) then v.syslog_message = $1; # Handle messages starting with date/time and key if (matches_regular_expression(v.syslog_message, '^([0-9]+-[0-9]+-[0-9]+) ([0-9]+:[0-9]+:[0-9]+) ([^ ]+) (.*)$')) then ( v.key = $3; set_collected_field(v.key, 'date', $1); set_collected_field(v.key, 'time', $2); v.message = $4; # 2008-02-01 - GMF - Trim off leading bracketed IP. # Not sure what this field is, but it breaks name=value parsing. if (matches_regular_expression(v.message, '^[[][0-9]+[.][0-9]+[.][0-9]+[.][0-9]+[]] (.*)$')) then v.message = $1; if (matches_regular_expression(v.message, '^<= ([^ ]*) (.*)$')) then ( v.sender = $1; v.name_value_pairs = $2; if (matches_regular_expression(v.sender, '^<([^>]*)>$')) then v.sender = $1; set_collected_field(v.key, 'sender', v.sender); ); # Handle <= lines # Handle a => line else if (matches_regular_expression(v.message, '^=> ([^ ]+) ([^ ]+) (.*)$')) then ( v.recipient_username = $1; v.recipient = $2; v.name_value_pairs = $3; # Check if recipient is really a N=value expression; if so, then $1 is the real recipient, # and the N=value section should be added back on to name_value_pairs. if (matches_regular_expression(v.recipient, '^[A-Z]=')) then ( v.name_value_pairs = v.recipient . ' ' . v.name_value_pairs; v.recipient = v.recipient_username; v.recipient_username = ""; ); # Strip off <> around recipient if (matches_regular_expression(v.recipient, '^<([^>]*)>')) then v.recipient = $1; set_collected_field(v.key, 'recipient_username', v.recipient_username); set_collected_field(v.key, 'recipient', v.recipient); ); # Handle => lines else if (v.message eq 'Completed') then ( accept_collected_entry(v.key, false); v.name_value_pairs = ''; ); # If the message starts with [A-Z]=, treat it as nothing but name/value pairs. else if (matches_regular_expression(v.message, '^[A-Z]=')) then v.name_value_pairs = v.message; # Handle any name/value pairs while ((v.name_value_pairs ne '') and (matches_regular_expression(v.name_value_pairs, '^([^=]+)=(.*)$'))) ( v.name = $1; if (v.name eq 'A') then v.name = 'authenticated_name'; else if (v.name eq 'C') then v.name = 'smtp_delivery_conf'; else if (v.name eq 'CV') then v.name = 'cert_verif_status'; else if (v.name eq 'DN') then v.name = 'dist_name_from_peer'; else if (v.name eq 'H') then v.name = 'hostname_ip'; else if (v.name eq 'I') then v.name = 'interface'; else if (v.name eq 'id') then v.name = 'message_id'; else if (v.name eq 'R') then v.name = 'router_name'; else if (v.name eq 'S') then v.name = 'size'; else if (v.name eq 'ST') then v.name = 'shadow_transport_name'; else if (v.name eq 'T') then v.name = 'subject'; else if (v.name eq 'P') then v.name = 'protocol'; else if (v.name eq 'U') then v.name = 'user_rfc1413'; else if (v.name eq 'X') then v.name = 'tls_cipher_suite'; else if (v.name eq 'F') then v.name = 'antibody_filter'; v.value_and_remainder = $2; if (matches_regular_expression(v.value_and_remainder, '^([^=]+) ([^ =]+=.*)$')) then ( v.value = $1; v.name_value_pairs = $2; ); else ( v.value = v.value_and_remainder; v.name_value_pairs = ''; ); if (v.name eq 'hostname_ip') then ( if (matches_regular_expression(v.value, '^([^ ]+) \\\\[([^]]+)\\\\]')) then ( set_collected_field(v.key, 'source_hostname', $1); set_collected_field(v.key, 'source_ip', $2); ); else if (matches_regular_expression(v.value, '^([^ ]+) \\\\*\\\\(unresolved\\\\)\\\\* \\\\[([^]]+) \\\\*\\\\(unresolved\\\\)\\\\*\\\\]')) then ( set_collected_field(v.key, 'source_hostname', $1); set_collected_field(v.key, 'source_ip', $2); ); else if (matches_regular_expression(v.value, '^([^ ]+) \\\\([0-9.]+ \\\\*\\\\(unresolved\\\\)\\\\*\\\\) \\\\[([^]]+) ')) then ( set_collected_field(v.key, 'source_hostname', $1); set_collected_field(v.key, 'source_ip', $2); ); ); else ( #echo(v.name . " = " . v.value); # debug set_collected_field(v.key, v.name, v.value); ); # If this was an antibody filter line, accept now. if (v.name eq 'antibody_filter') then ( set_collected_field(v.key, 'messages_filtered', 1); accept_collected_entry(v.key, false); ); ); # while pair ); # if matches header ` # Database fields database.fields = { date_time = "" day_of_week = "" hour_of_day = "" sender = "" recipient = "" recipient_username = "" subject = "" protocol = "" transport_name = "" source_hostname = "" source_ip = "" location = "" router_name = "" source_ip = "" authenticated_name = "" smtp_delivery_conf = "" cert_verif_status = "" dist_name_from_peer = "" shadow_transport_name = "" user_rfc1413 = "" tls_cipher_suite = "" antibody_filter = "" } # database.fields database.numerical_fields = { messages = { default = true requires_log_field = false entries_field = true } # messages size = { type = "float" display_format_type = "bandwidth" } # size messages_filtered = "" } # database.numerical_fields log.filters = { mark_entry = { label = '$lang_admin.log_filters.mark_entry_label' comment = '$lang_admin.log_filters.mark_entry_comment' value = 'messages = 1;' } # mark_entry } # log.filters create_profile_wizard_options = { date_time_tracking = true # How the reports should be grouped in the report menu report_groups = { date_time_group = "" sender = true recipient = true recipient_username = true subject = true protocol = true transport_name = true source_hostname = true source_ip = true router_name = true } # report_groups } # create_profile_wizard_options } # exim_4