<?xml version="1.0" encoding="utf-8"?>
<?xml-stylesheet type="text/css" href="http://commons.oreilly.com/wiki/skins/common/feed.css?97"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
		<id>http://commons.oreilly.com/wiki/index.php?title=SpamAssassin/Integrating_SpamAssassin_with_Exim&amp;action=history&amp;feed=atom</id>
		<title>SpamAssassin/Integrating SpamAssassin with Exim - Revision history</title>
		<link rel="self" type="application/atom+xml" href="http://commons.oreilly.com/wiki/index.php?title=SpamAssassin/Integrating_SpamAssassin_with_Exim&amp;action=history&amp;feed=atom"/>
		<link rel="alternate" type="text/html" href="http://commons.oreilly.com/wiki/index.php?title=SpamAssassin/Integrating_SpamAssassin_with_Exim&amp;action=history"/>
		<updated>2013-06-19T10:14:04Z</updated>
		<subtitle>Revision history for this page on the wiki</subtitle>
		<generator>MediaWiki 1.11.0</generator>

	<entry>
		<id>http://commons.oreilly.com/wiki/index.php?title=SpamAssassin/Integrating_SpamAssassin_with_Exim&amp;diff=5287&amp;oldid=prev</id>
		<title>Docbook2Wiki: Initial conversion from Docbook</title>
		<link rel="alternate" type="text/html" href="http://commons.oreilly.com/wiki/index.php?title=SpamAssassin/Integrating_SpamAssassin_with_Exim&amp;diff=5287&amp;oldid=prev"/>
				<updated>2008-03-07T10:56:42Z</updated>
		
		<summary type="html">&lt;p&gt;Initial conversion from Docbook&lt;/p&gt;

			&lt;table style=&quot;background-color: white; color:black;&quot;&gt;
			&lt;col class='diff-marker' /&gt;
			&lt;col class='diff-content' /&gt;
			&lt;col class='diff-marker' /&gt;
			&lt;col class='diff-content' /&gt;
			&lt;tr&gt;
				&lt;td colspan='2' style=&quot;background-color: white; color:black;&quot;&gt;←Older revision&lt;/td&gt;
				&lt;td colspan='2' style=&quot;background-color: white; color:black;&quot;&gt;Revision as of 10:56, 7 March 2008&lt;/td&gt;
			&lt;/tr&gt;
		&lt;/table&gt;</summary>
		<author><name>Docbook2Wiki</name></author>	</entry>

	<entry>
		<id>http://commons.oreilly.com/wiki/index.php?title=SpamAssassin/Integrating_SpamAssassin_with_Exim&amp;diff=5233&amp;oldid=prev</id>
		<title>Docbook2Wiki: Initial conversion from Docbook</title>
		<link rel="alternate" type="text/html" href="http://commons.oreilly.com/wiki/index.php?title=SpamAssassin/Integrating_SpamAssassin_with_Exim&amp;diff=5233&amp;oldid=prev"/>
				<updated>2008-03-07T10:53:32Z</updated>
		
		<summary type="html">&lt;p&gt;Initial conversion from Docbook&lt;/p&gt;
&lt;p&gt;&lt;b&gt;New page&lt;/b&gt;&lt;/p&gt;&lt;div&gt;{{SpamAssassin/TOC}}&lt;br /&gt;
Exim is an MTA developed by Philip Hazel at the University of Cambridge. Exim is designed for Internet mail hosts and provides flexibility, performance, and strong access controls. It has become a popular replacement for sendmail because it provides a compatible command-line interface.&lt;br /&gt;
&lt;br /&gt;
This chapter explains how to integrate SpamAssassin into an Exim-based mail server to perform spam-checking for local recipients or to create a spam-checking mail gateway.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;warning&amp;quot;&amp;gt;&lt;br /&gt;
'''Warning'''&lt;br /&gt;
&lt;br /&gt;
Exim is a complex piece of software and, more than most MTAs, has an extensive and complicated set of configuration options. This chapter assumes that you are running Exim 4 and does not cover how to securely install, configure, or operate Exim itself. For that information, see the Exim documentation, the web site ''http://www.exim.org'', and the book ''The Exim SMTP Mail Server: Official Guide for Release 4''by Philip Hazel (UIT Cambridge).&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Exim consists primarily of a single ''setuid'' executable, &amp;lt;tt&amp;gt;exim&amp;lt;/tt&amp;gt;, that performs different functions depending on its command-line arguments. These functions include listening on the SMTP port and receiving and enqueuing incoming messages, adding locally generated messages to the queue, and processing the queue to transmit outgoing messages. When compiled from source code, &amp;lt;tt&amp;gt;exim&amp;lt;/tt&amp;gt; is installed in ''/usr/exim/bin'', and the examples in this chapter assume that directory is used.&lt;br /&gt;
&lt;br /&gt;
Exim's configuration file defaults to ''/usr/exim/configure''. The configuration file determines the behavior of Exim and defines three important logical entities: ''access control lists (ACLs)'', ''routers'', and ''transports''. ACLs define tests that can be performed during incoming SMTP sessions to determine whether Exim will accept a message. Routers determine how messages to a given address should be delivered (or rewritten to new addresses) and queue them up for transports. Transports define delivery mechanisms—methods by which a message can be copied from Exim's queue to a local mailbox, a remote host, or elsewhere. Each of these entities has its own section in the configuration file.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;tip&amp;quot;&amp;gt;&lt;br /&gt;
'''Tip'''&lt;br /&gt;
&lt;br /&gt;
While you can define ACLs and transports in any order, you must define routers in the order in which they are to run. In the default configuration, the router order is &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt; (look up remote hostnames and route messages via SMTP), &amp;lt;tt&amp;gt;system_aliases&amp;lt;/tt&amp;gt; (redirect messages on the basis of the ''/etc/aliases'' file), &amp;lt;tt&amp;gt;userforward&amp;lt;/tt&amp;gt; (redirect messages on the basis of user ''.forward'' files), and &amp;lt;tt&amp;gt;localuser&amp;lt;/tt&amp;gt; (route message via the local delivery agent).&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Spam-Checking via procmail ==&lt;br /&gt;
&lt;br /&gt;
One easy way to add SpamAssassin to an Exim system is to configure Exim to use procmail as its local delivery agent. Then add a procmail recipe for spam-tagging to ''/etc/procmailrc''.&lt;br /&gt;
&lt;br /&gt;
The advantages of this approach are&lt;br /&gt;
&lt;br /&gt;
* It's very easy to set up.&lt;br /&gt;
* You can run &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt;, and the procmail recipe can use &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; for faster spam-checking.&lt;br /&gt;
* User preference files, autowhitelists, and Bayesian databases can be used.&lt;br /&gt;
&lt;br /&gt;
However, Exim runs a local delivery agent only for email destined for a local recipient. You cannot create a spam-checking gateway with this approach.&lt;br /&gt;
&lt;br /&gt;
To configure Exim to use procmail for local delivery, add the following transport to the Exim configuration file (in the transports section):&lt;br /&gt;
&lt;br /&gt;
   procmail_pipe:&lt;br /&gt;
     driver = pipe&lt;br /&gt;
     command = ''/usr/local/bin/procmail'' -d $local_part&lt;br /&gt;
     return_path_add&lt;br /&gt;
     delivery_date_add&lt;br /&gt;
     envelope_to_add&lt;br /&gt;
     check_string = &amp;quot;From &amp;quot;&lt;br /&gt;
     escape_string = &amp;quot;&amp;gt;From &amp;quot;&lt;br /&gt;
     user = $local_part&lt;br /&gt;
     group = ''mail''&lt;br /&gt;
          &lt;br /&gt;
&lt;br /&gt;
Ensure that you provide the proper path to procmail and an appropriate group for running procmail in the definition of the &amp;lt;tt&amp;gt;procmail_pipe&amp;lt;/tt&amp;gt; transport.&lt;br /&gt;
&lt;br /&gt;
Next add a new router to direct messages to the &amp;lt;tt&amp;gt;procmail_pipe&amp;lt;/tt&amp;gt; transport. This router should be added to the routers section of the configuration file before (or in place of) the &amp;lt;tt&amp;gt;localuser&amp;lt;/tt&amp;gt; router, which is usually the last router.&lt;br /&gt;
&lt;br /&gt;
   procmail:&lt;br /&gt;
     driver = accept&lt;br /&gt;
     check_local_user&lt;br /&gt;
     transport = procmail_pipe&lt;br /&gt;
     cannot_route_message = Unknown user&lt;br /&gt;
     no_verify&lt;br /&gt;
     no_expn&lt;br /&gt;
&lt;br /&gt;
Local addresses that reach the &amp;lt;tt&amp;gt;procmail&amp;lt;/tt&amp;gt; router will be accepted and delivered via the &amp;lt;tt&amp;gt;procmail_pipe&amp;lt;/tt&amp;gt; transport, which invokes procmail in its role as a local delivery agent.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;warning&amp;quot;&amp;gt;&lt;br /&gt;
'''Warning'''&lt;br /&gt;
&lt;br /&gt;
After any change to the Exim configuration file, you must send a SIGHUP signal to the Exim daemon to cause it to reread the configuration file. You can test configuration changes before you do this by running &amp;lt;tt&amp;gt;exim -bV&amp;lt;/tt&amp;gt;.&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Next, configure procmail to invoke SpamAssassin. If you want to invoke SpamAssassin on behalf of every user, do so by editing the ''/etc/procmailrc'' file. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-1|Example 8-1]] shows an ''/etc/procmailrc''that invokes SpamAssassin.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-1&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-1. A complete /etc/procmailrc'''&lt;br /&gt;
&lt;br /&gt;
 DROPPRIVS=yes&lt;br /&gt;
 PATH=/bin:/usr/bin:/usr/local/bin&lt;br /&gt;
 SHELL=/bin/sh&lt;br /&gt;
 &lt;br /&gt;
 # Spamassassin&lt;br /&gt;
 :0fw&lt;br /&gt;
 * &amp;lt;300000&lt;br /&gt;
 |/usr/bin/spamassassin&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
If you run &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt;, replace the call to &amp;lt;tt&amp;gt;spamassassin&amp;lt;/tt&amp;gt; in ''procmailrc'' with a call to &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; instead. Using &amp;lt;tt&amp;gt;spamc/spamd&amp;lt;/tt&amp;gt; significantly improves performance on most systems but makes it more difficult to enable users to write their own rules.&lt;br /&gt;
&lt;br /&gt;
== Spam-Checking All Incoming Mail ==&lt;br /&gt;
&lt;br /&gt;
If you want to set up a spam-checking gateway for all recipients, local or not, you need a way to perform spam-checking as mail is received, before final delivery. Exim provides three different ways to do this: via routers, via exiscan, and via defining a &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; function.&lt;br /&gt;
&lt;br /&gt;
In a router-based configuration, SpamAssassin is invoked after Exim has received a message during the process of routing each delivery address in the message. If the message is destined for a local user, SpamAssassin can use per-user preference files; if the message will be relayed to a remote user, SpamAssassin still checks the message using sitewide settings. In this configuration, SpamAssassin may be invoked several times for each message received (once for each message recipient). [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-FIG-1|Figure 8-1]] illustrates this configuration.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-FIG-1&amp;quot;&amp;gt;&lt;br /&gt;
'''Figure 8-1. A router-based configuration for spam-checking in Exim'''&lt;br /&gt;
&lt;br /&gt;
[[Image:SpamAssassin_I_8_tt145.png|A router-based configuration for spam-checking in Exim]]&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In an ''exiscan'' configuration, Exim invokes SpamAssassin during the SMTP transaction by means of a new ACL. Messages that SpamAssassin considers spam can be rejected before the SMTP transaction is complete, or accepted and tagged. However, you cannot use per-user preferences in this configuration without negatively impacting performance. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-FIG-2|Figure 8-2]] illustrates this approach.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-FIG-2&amp;quot;&amp;gt;&lt;br /&gt;
'''Figure 8-2. An exiscan-based configuration for spam-checking in Exim'''&lt;br /&gt;
&lt;br /&gt;
[[Image:SpamAssassin_I_8_tt146.png|An exiscan-based configuration for spam-checking in Exim]]&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In a configuration using &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt;, Exim invokes SpamAssassin during the SMTP transaction when it calls the &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; function for the incoming message. The message can be accepted or rejected in the SMTP transaction; if &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; accepts the message, tagging headers can be added. Other interesting effects, including teergrubing—responding very slowly during the SMTP transaction when spam is detected in order to tie up the spammer's MTA—are possible with this approach, but it is difficult to use per-user preferences in this configuration. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-FIG-3|Figure 8-3]] illustrates this approach.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-FIG-3&amp;quot;&amp;gt;&lt;br /&gt;
'''Figure 8-3. A local_scan( )-based configuration for spam-checking in Exim'''&lt;br /&gt;
&lt;br /&gt;
[[Image:SpamAssassin_I_8_tt147.png|A local_scan( )-based configuration for spam-checking in Exim]]&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Each of these methods is described in detail in the following sections.&lt;br /&gt;
&lt;br /&gt;
== Using Routers and Transports ==&lt;br /&gt;
&lt;br /&gt;
You can configure Exim to pass all incoming mail through SpamAssassin by writing a transport that pipes messages to SpamAssassin and then reinjects them into Exim, and a router that directs messages to the transport. To prevent the reinjected messages from being spam-checked again, you can set their &amp;lt;tt&amp;gt;$received_protocol&amp;lt;/tt&amp;gt; to indicate they've been checked when you reinject them, and use the &amp;lt;tt&amp;gt;$received_protocol&amp;lt;/tt&amp;gt; value as a condition to determine whether or not the router will send them for checking.&lt;br /&gt;
&lt;br /&gt;
=== Configuring the Transport ===&lt;br /&gt;
&lt;br /&gt;
[[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-2|Example 8-2]] shows the configuration of the transport in ''/usr/exim/configure''.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-2&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-2. A transport for spam-checking'''&lt;br /&gt;
&lt;br /&gt;
 spamassassin:&lt;br /&gt;
   driver = pipe&lt;br /&gt;
   use_bsmtp = true&lt;br /&gt;
   command = /usr/exim/bin/exim -bS -oMr sa-checked&lt;br /&gt;
   transport_filter = /usr/bin/spamc -f&lt;br /&gt;
   home_directory = &amp;quot;/tmp&amp;quot;&lt;br /&gt;
   current_directory = &amp;quot;/tmp&amp;quot;&lt;br /&gt;
   user = exim&lt;br /&gt;
   group = exim&lt;br /&gt;
   log_output = true&lt;br /&gt;
   return_fail_output = true&lt;br /&gt;
   return_path_add = false&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;spamassassin&amp;lt;/tt&amp;gt; transport in [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-2|Example 8-2]] uses Exim's &amp;lt;tt&amp;gt;pipe&amp;lt;/tt&amp;gt; driver to deliver a message to a command. The example specifies that Exim should use the batched SMTP (BSMTP) format to transmit the message. The command is another invocation of &amp;lt;tt&amp;gt;exim&amp;lt;/tt&amp;gt; itself, with the &amp;lt;tt&amp;gt;-bS&amp;lt;/tt&amp;gt; option to accept BSMTP input and the &amp;lt;tt&amp;gt;-oMr sa-checked&amp;lt;/tt&amp;gt; option to set the &amp;lt;tt&amp;gt;$received_protocol&amp;lt;/tt&amp;gt; variable to &amp;lt;tt&amp;gt;sa-checked&amp;lt;/tt&amp;gt;. Before Exim pipes the message to the command, it filters the message through the program specified by &amp;lt;tt&amp;gt;transport_filter&amp;lt;/tt&amp;gt;—in this case, &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt;—and uses the output of the filter as the message to deliver. The other transport options provide home and working directories for running the command, specify that the command should be run as user and group ''exim'', cause command output to be logged and any failure messages to be included in a bounce message, and indicate that a ''Return-Path'' header should not be added (because this transport is not performing final delivery).&lt;br /&gt;
&lt;br /&gt;
You must specify that the &amp;lt;tt&amp;gt;exim&amp;lt;/tt&amp;gt; command used in the transport will be run as one of Exim's trusted users in order for the &amp;lt;tt&amp;gt;-oMr sa-checked&amp;lt;/tt&amp;gt; option to work. The Exim user (specified during Exim's installation) is always trusted. You can add other trusted users in the configuration file with the &amp;lt;tt&amp;gt;trusted_users&amp;lt;/tt&amp;gt; or &amp;lt;tt&amp;gt;trusted_groups&amp;lt;/tt&amp;gt; directives.&lt;br /&gt;
&lt;br /&gt;
=== Configuring the Router ===&lt;br /&gt;
&lt;br /&gt;
The transport provides a mechanism for Exim to filter messages through SpamAssassin and reinject them. You must also define a router that will invoke this transport during delivery. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-3|Example 8-3]] displays a definition for such a router in ''/usr/exim/configure''.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-3&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-3. A spam-checking router in Exim'''&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;spamassassin_router:&lt;br /&gt;
  driver = accept&lt;br /&gt;
  transport = spamassassin&lt;br /&gt;
  condition = &amp;quot;${if {!eq {$received_protocol}{sa-checked}} {1} {0}}&amp;quot;&lt;br /&gt;
  no_verify&lt;br /&gt;
  no_expn&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt; in [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-3|Example 8-3]] uses the &amp;lt;tt&amp;gt;accept&amp;lt;/tt&amp;gt; driver, which simply delivers a message to a transport. The &amp;lt;tt&amp;gt;transport&amp;lt;/tt&amp;gt; directive specifies our &amp;lt;tt&amp;gt;spamassassin&amp;lt;/tt&amp;gt; transport. The &amp;lt;tt&amp;gt;condition&amp;lt;/tt&amp;gt; directive prevents a spam-checking loop when messages are reinjected by insuring that the value of &amp;lt;tt&amp;gt;$received_protocol&amp;lt;/tt&amp;gt; is not &amp;lt;tt&amp;gt;sa-checked&amp;lt;/tt&amp;gt;. The &amp;lt;tt&amp;gt;no_verify&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;no_expn&amp;lt;/tt&amp;gt; directives instruct Exim to skip this router when performing address verification or expansion.&lt;br /&gt;
&lt;br /&gt;
Add the router definition from [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-3|Example 8-3]] to the section of ''/usr/exim/configure''that lists routers. The order of the router definitions is significant. Where you add the &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt; router in the list determines which messages will be checked, as shown in [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-TABLE-1|Table 8-1]]. Most sites will probably want to add the router between &amp;lt;tt&amp;gt;system_aliases&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;userforward&amp;lt;/tt&amp;gt; (or possibly between &amp;lt;tt&amp;gt;userforward&amp;lt;/tt&amp;gt; and a procmail router), but spam-checking gateways are likely to need the router before &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt; as nearly all of their mail will be destined for remote sites.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-TABLE-1&amp;quot;&amp;gt;&lt;br /&gt;
'''Table 8-1. Effect of the position of spamassassin_router in the Exim router list'''&lt;br /&gt;
&lt;br /&gt;
{| border=&amp;quot;1&amp;quot; &lt;br /&gt;
|-&lt;br /&gt;
! Position !! Effect&lt;br /&gt;
|-&lt;br /&gt;
| First in the list (before &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt;) || SpamAssassin invoked on all messages, including local deliveries, outgoing messages, and messages relayed to remote hosts.&lt;br /&gt;
|-&lt;br /&gt;
| Between &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;system_aliases&amp;lt;/tt&amp;gt; || SpamAssassin invoked on messages with addresses in locally hosted domains. System aliases and user ''.forward'' files will receive messages already spam-checked (and can act on tagging).&lt;br /&gt;
|-&lt;br /&gt;
| Between &amp;lt;tt&amp;gt;system_aliases&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;userforward&amp;lt;/tt&amp;gt; || SpamAssassin invoked on messages with addresses in locally hosted domains, unless system alias file redirected them to a remote host. User ''.forward'' files will receive messages already spam-checked (and can act on tagging).&lt;br /&gt;
|-&lt;br /&gt;
| Between &amp;lt;tt&amp;gt;userforward&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;localuser&amp;lt;/tt&amp;gt; || SpamAssassin invoked only on messages that will be delivered locally. User ''.forward'' files will receive messages without spam-checking. Spam-checked messages will be delivered to local mailbox.&lt;br /&gt;
|-&lt;br /&gt;
| After &amp;lt;tt&amp;gt;localuser&amp;lt;/tt&amp;gt; || Too late&amp;amp;#33; Messages will already have been delivered.&lt;br /&gt;
|}&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Using Per-User Spam-Checking Preferences ===&lt;br /&gt;
&lt;br /&gt;
Because Exim routes each delivery address separately, you can configure it to behave differently for messages that will be delivered locally and messages that will be relayed to remote hosts. You can take advantage of this flexibility to direct SpamAssassin to use per-user preferences when checking a message that is destined for a local user and to use sitewide preferences when checking a message that is destined for a remote user. This approach requires a second transport and a second router. Add another transport such as that shown in [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-4|Example 8-4]] to your Exim configuration file.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-4&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-4. Transport for local spam-checking in Exim'''&lt;br /&gt;
&lt;br /&gt;
 spamassassin_local:&lt;br /&gt;
   driver = pipe&lt;br /&gt;
   use_bsmtp = true&lt;br /&gt;
   command = /usr/exim/bin/exim -bS -oMr sa-checked&lt;br /&gt;
   '''transport_filter = /usr/bin/spamc -f -u $local_part'''&lt;br /&gt;
   home_directory = &amp;quot;/tmp&amp;quot;&lt;br /&gt;
   current_directory = &amp;quot;/tmp&amp;quot;&lt;br /&gt;
   user = exim&lt;br /&gt;
   group = exim&lt;br /&gt;
   log_output = true&lt;br /&gt;
   return_fail_output = true&lt;br /&gt;
   return_path_add = false&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The key addition in the &amp;lt;tt&amp;gt;spamassassin_local&amp;lt;/tt&amp;gt; transport is the use of &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt;'s &amp;lt;tt&amp;gt;-u&amp;lt;/tt&amp;gt; &amp;lt;tt&amp;gt;''user''&amp;lt;/tt&amp;gt; command-line option to specify the user on whose behalf &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; is running. &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; will convey the username to &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt;, which will examine the user's ''.spamassassin/user_prefs'' file for preferences.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;warning&amp;quot;&amp;gt;&lt;br /&gt;
'''Warning'''&lt;br /&gt;
&lt;br /&gt;
For this transport to work, &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; must be able to read users' preference files. Because you should run &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; under a dedicated user and group, this user or group must be able to search the ''.spamassassin''subdirectory of each user's home directory and read the ''user_prefs'' file. (You may instead run &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; as ''root'', but using a dedicated user is a better security practice.)&lt;br /&gt;
&lt;br /&gt;
You must not invoke &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; with the &amp;lt;tt&amp;gt;--nouser-config&amp;lt;/tt&amp;gt; or &amp;lt;tt&amp;gt;--auth-ident&amp;lt;/tt&amp;gt; options when using this transport. If you use &amp;lt;tt&amp;gt;--nouser-config&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; will ignore &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt;'s &amp;lt;tt&amp;gt;-u&amp;lt;/tt&amp;gt; argument, and user preferences will not be examined. If you use &amp;lt;tt&amp;gt;--auth-ident&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; will attempt to confirm that &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; is being run by the user given in its &amp;lt;tt&amp;gt;-u&amp;lt;/tt&amp;gt; argument. Because Exim runs as its own user, the authentication will fail and &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; will refuse to look up user preferences.&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Next, add a router that uses the &amp;lt;tt&amp;gt;spamassassin_local&amp;lt;/tt&amp;gt; transport, as shown in [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-5|Example 8-5]].&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-5&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-5. A spam-checking router with user preferences in Exim'''&lt;br /&gt;
&lt;br /&gt;
 spamassassin_local_router:&lt;br /&gt;
   driver = accept&lt;br /&gt;
   '''transport = spamassassin_local'''&amp;lt;nowiki&amp;gt;&lt;br /&gt;
  condition = &amp;quot;${if {!eq {$received_protocol}{sa-checked}} {1} {0}}&amp;quot;&lt;br /&gt;
  no_verify&lt;br /&gt;
  no_expn&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You should also modify &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt; to limit its use to non-local domains. This modification is shown in [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-6|Example 8-6]].&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-6&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-6. A spam-checking router for non-local domains in Exim'''&lt;br /&gt;
&lt;br /&gt;
 spamassassin_router:&lt;br /&gt;
   driver = accept&lt;br /&gt;
   transport = spamassassin&lt;br /&gt;
   '''domains = ! +local_domains'''&amp;lt;nowiki&amp;gt;&lt;br /&gt;
  condition = &amp;quot;${if {!eq {$received_protocol}{sa-checked}} {1} {0}}&amp;quot;&lt;br /&gt;
  no_verify&lt;br /&gt;
  no_expn&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Arrange the routers in the following order:&lt;br /&gt;
&lt;br /&gt;
# &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt;, to perform spam-checking for messages addressed to remote domains&lt;br /&gt;
# &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt;, to route messages addressed to remote domains via SMTP&lt;br /&gt;
# &amp;lt;tt&amp;gt;system_aliases&amp;lt;/tt&amp;gt;, to redirect messages with addresses in ''/etc/aliases''&lt;br /&gt;
# &amp;lt;tt&amp;gt;spamassassin_local_router&amp;lt;/tt&amp;gt;, to perform spam-checking for messages addressed to local users with the per-user preferences of the local user (who may, however, choose to forward the tagged message elsewhere)&lt;br /&gt;
# &amp;lt;tt&amp;gt;userforward&amp;lt;/tt&amp;gt;, to redirect messages with addresses in user ''.forward'' files&lt;br /&gt;
# &amp;lt;tt&amp;gt;localuser&amp;lt;/tt&amp;gt;, to route messages via the local delivery agent&lt;br /&gt;
&lt;br /&gt;
To illustrate how this approach functions, consider an Exim system running on ''mail.example.com'' and configured to relay messages for ''example.com'' to an internal mail server. On ''mail.example.com'', ''postmaster'' is an alias for the local user ''chris''. When a spammer sends a message addressed to ''sam@example.com'' and ''postmaster@mail.example.com'', Exim passes each address through its list of routers. ''sam@example.com'' is routed by &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt;, so a copy of the message is tagged by SpamAssassin using its sitewide configuration and then reinjected. The reinjected message bypasses &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt; and is routed by &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt;, which queues it for remote delivery. Meanwhile, ''postmaster@mail.example.com'' is destined for a local domain and bypasses both &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt;. The &amp;lt;tt&amp;gt;system_aliases&amp;lt;/tt&amp;gt; router rewrites the address to ''chris@mail.example.com'', which Exim then begins routing. This address bypasses &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt;, and &amp;lt;tt&amp;gt;system_alias&amp;lt;/tt&amp;gt; and is routed by &amp;lt;tt&amp;gt;spamassassin_local_router&amp;lt;/tt&amp;gt;, which tags a copy of the message using ''chris'''s SpamAssassin preferences and reinjects it. The reinjected message bypasses &amp;lt;tt&amp;gt;spamassassin_router&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;system_alias&amp;lt;/tt&amp;gt;, and &amp;lt;tt&amp;gt;spamassassin_local_router&amp;lt;/tt&amp;gt;, and assuming ''chris'' does not have a ''.forward'' file, Exim delivers it to ''chris'''s local mailbox. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-FIG-4|Figure 8-4]] illustrates this process.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-FIG-4&amp;quot;&amp;gt;&lt;br /&gt;
'''Figure 8-4. Exim router lookups during delivery'''&lt;br /&gt;
&lt;br /&gt;
[[Image:SpamAssassin_I_8_tt148.png|Exim router lookups during delivery]]&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Using exiscan ==&lt;br /&gt;
&lt;br /&gt;
One of Exim's most powerful and flexible features is its ACL system. Each ACL is a set of rules or tests that Exim performs when receiving a message; for example, an ACL is available for each stage of the SMTP transaction (start of connection, after HELO, after MAIL FROM, etc.). Rules are evaluated in order until one matches, and the associated action is then performed. Actions can include allowing the transaction to proceed, deferring the transaction, rejecting the transaction, ignoring the transaction, adding warning headers to the message, or dropping the connection altogether. If no rule matches, the ACL rejects the corresponding portion of the SMTP transaction.&lt;br /&gt;
&lt;br /&gt;
exiscan is a set of patches for Exim that introduces the ability to invoke SpamAssassin in the &amp;lt;tt&amp;gt;acl_smtp_data&amp;lt;/tt&amp;gt; ACL that Exim consults after the DATA step of an SMTP transaction. You can download exiscan from ''http://duncanthrax.net/exiscan-acl/''; many precompiled versions of Exim (e.g., in Linux distributions) have the patch already applied. exiscan's new ACL actions also include blocking MIME attachments, virus-checking, and checking headers against regular expressions.&lt;br /&gt;
&lt;br /&gt;
=== Installing exiscan ===&lt;br /&gt;
&lt;br /&gt;
If you're not using a version of Exim that has exiscan already compiled in, you should download the exiscan patch file and apply it to your Exim source code with the GNU &amp;lt;tt&amp;gt;patch&amp;lt;/tt&amp;gt; program. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-7|Example 8-7]] shows the patch process, assuming that both the Exim source code and the patch are in ''/usr/local/src''. Stop and restart Exim after you install the patched version.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-7&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-7. Patching the Exim source code with exiscan'''&lt;br /&gt;
&lt;br /&gt;
 $ '''cd /usr/local/src/exim-4.30'''&lt;br /&gt;
 $ '''patch -p1 -s &amp;lt; ../exiscan-acl-4.30-14.patch'''&lt;br /&gt;
 $ '''rm -rf build-*'''&lt;br /&gt;
 $ '''make'''&lt;br /&gt;
 ...Compilation messages...&lt;br /&gt;
 $ '''su'''&lt;br /&gt;
 Password: &lt;br /&gt;
 '''                     XXXXXXXX'''&lt;br /&gt;
 '''                  '''&lt;br /&gt;
 # '''make install'''&lt;br /&gt;
                &lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;tip&amp;quot;&amp;gt;&lt;br /&gt;
'''Tip'''&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;rm -rf build-*&amp;lt;/tt&amp;gt; command removes any old Exim build directories that may be present and forces Exim's ''Makefile'' to recreate them and repopulate them with symbolic links to source code files. This is important, because exiscan adds new source code files that would otherwise not have links in the build directory.&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Writing acl_smtp_data ===&lt;br /&gt;
&lt;br /&gt;
exiscan extends Exim's ACL language by adding a new rule, &amp;lt;tt&amp;gt;spam&amp;lt;/tt&amp;gt;, that makes a connection to &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; to request a message check on behalf of a specified user and returns true if the message would exceed the user's SpamAssassin spam threshold. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-8|Example 8-8]] shows a simple &amp;lt;tt&amp;gt;acl_smtp_data&amp;lt;/tt&amp;gt; that uses the &amp;lt;tt&amp;gt;spam&amp;lt;/tt&amp;gt; condition to add an ''X-Spam-Flag: YES'' header to spam messages.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-8&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-8. Adding an X-Spam-Flag header with exiscan'''&lt;br /&gt;
&lt;br /&gt;
 acl_smtp_data:&lt;br /&gt;
 &lt;br /&gt;
   warn  message = X-Spam-Flag: YES&lt;br /&gt;
         spam = nobody&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In this ACL, the condition &amp;lt;tt&amp;gt;spam = nobody&amp;lt;/tt&amp;gt; invokes &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; as the user ''nobody''. If the message's spam score exceeds ''nobody'''s threshold, Exim takes the &amp;lt;tt&amp;gt;warn&amp;lt;/tt&amp;gt; action, adding the ''X-Spam-Flag'' header. Similarly, the following ACL rule will generate a second ''Subject'' header with a spam tag for spam messages.&lt;br /&gt;
&lt;br /&gt;
 warn  message = Subject: *SPAM* $h_Subject&lt;br /&gt;
       spam = nobody&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;tip&amp;quot;&amp;gt;&lt;br /&gt;
'''Tip'''&lt;br /&gt;
&lt;br /&gt;
ACLs can add headers but cannot remove them or modify them ''in situ''. To ''replace'' the ''Subject'' header with a tagged version, you must add a new header through the ACL (e.g., ''X-Spam-Subject'') and direct Exim's system filter to replace the message subject with the new header if it's present. An example of how to do this is included with the exiscan documentation.&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;spam&amp;lt;/tt&amp;gt; condition also sets several useful Exim variables as a side effect:&lt;br /&gt;
&lt;br /&gt;
;&amp;lt;tt&amp;gt;$spam_bar&amp;lt;/tt&amp;gt;&lt;br /&gt;
: If SpamAssassin gives a message a positive spam score, exiscan sets this variable to a string of plus (+) characters, with one plus for each point of spam score, up to 50. If SpamAssassin gives a message a negative spam score, exiscan sets this variable to a string of minus characters (-), with one minus for each negative point of spam score. If SpamAssassin gives a message a zero spam score, exiscan sets this variable to a slash (/) character.&lt;br /&gt;
;&amp;lt;tt&amp;gt;$spam_report&amp;lt;/tt&amp;gt;&lt;br /&gt;
: The full SpamAssassin report on a message.&lt;br /&gt;
;&amp;lt;tt&amp;gt;$spam_score&amp;lt;/tt&amp;gt;&lt;br /&gt;
: The score assigned to a message by SpamAssassin.&lt;br /&gt;
;&amp;lt;tt&amp;gt;$spam_score_int&amp;lt;/tt&amp;gt;&lt;br /&gt;
: The score assigned to a message by SpamAssassin multiplied by 10. exiscan stores this variable in the message's spool file, so Exim can use this value in later processing (e.g., in routers) to handle high-scoring messages differently than low-scoring messages.&lt;br /&gt;
&lt;br /&gt;
These variables can be used with &amp;lt;tt&amp;gt;warn&amp;lt;/tt&amp;gt; or &amp;lt;tt&amp;gt;deny&amp;lt;/tt&amp;gt; actions to implement several kinds of spam policies. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-9|Example 8-9]], adapted from the exiscan documentation, shows how you can direct Exim to add an ''X-Spam-Score'' header for all messages, to add an ''X-Spam-Report'' header for spam, and to reject a message completely if the spam score is higher than 12.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-9&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-9. Spam policies with exiscan'''&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;warn  message = X-Spam-Report: $spam_report&lt;br /&gt;
      spam = nobody&lt;br /&gt;
&lt;br /&gt;
warn  message = X-Spam-Score: $spam_score ($spam_bar)&lt;br /&gt;
      spam = nobody:true&lt;br /&gt;
&lt;br /&gt;
deny   message = This message scored $spam_score spam points.&lt;br /&gt;
       spam = nobody&lt;br /&gt;
       condition = ${if &amp;gt;{$spam_score_int}{120}{1}{0}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The first rule performs spam-checking and adds the ''X-Spam-Report'' header if a message exceeds the spam threshold. exiscan caches the spam-checking results, so future calls to the &amp;lt;tt&amp;gt;spam&amp;lt;/tt&amp;gt; condition for this message will not actually recheck the message. The second rule uses the &amp;lt;tt&amp;gt;:true&amp;lt;/tt&amp;gt; option, which causes the condition to be evaluated as true regardless of the results of the spam check. Accordingly, Exim will add an ''X-Spam-Score'' header to all messages. Finally, Exim executes the &amp;lt;tt&amp;gt;deny&amp;lt;/tt&amp;gt; action (refusing the message with the given text added to the SMTP rejection response) if the &amp;lt;tt&amp;gt;$spam_score_int&amp;lt;/tt&amp;gt; is greater than 120 (which corresponds to a SpamAssassin score greater than 12.0).&lt;br /&gt;
&lt;br /&gt;
=== Using Per-User Preferences ===&lt;br /&gt;
&lt;br /&gt;
Because exiscan checks messages for spam just once—at message receipt after the SMTP DATA command—it's difficult to use SpamAssassin's per-user preference files. Messages may have multiple recipients, some of whom are not local, and exiscan will not be able to determine whose preferences should be used.&lt;br /&gt;
&lt;br /&gt;
You can continue to use per-user preferences with exiscan in two ways, but each comes at a performance cost.&lt;br /&gt;
&lt;br /&gt;
* You can ensure that each email message will have only a single recipient by writing an ACL for the SMTP RCPT TO phase that defers all recipients except the first one. The sending MTA will retry delivery to the deferred recipients but may not do so immediately. As a result, some copies of messages with multiple recipients may be significantly delayed. The exiscan documentation includes an example of how to do this.&lt;br /&gt;
* You can use exiscan to perform initial spam-checking and refuse messages with high scores, and then use the router/transport approach described earlier to reinvoke SpamAssassin on the remaining messages for local recipients. This approach results in an extra &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; connection for each message with a local recipient but might be worthwhile if exiscan can refuse enough very obvious spam sent to multiple recipients.&lt;br /&gt;
&lt;br /&gt;
== Using sa-exim ==&lt;br /&gt;
&lt;br /&gt;
Exim calls its &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; function once just before accepting a message (via SMTP or from a local process). By default, this function does nothing—the implementation of the function in Exim's source code simply instructs Exim to accept the message. What makes &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; powerful is that you can replace Exim's version with your own code to perform custom message-checking. This function can be a good place to perform spam-checking.&lt;br /&gt;
&lt;br /&gt;
Even better, you don't have to write a new &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; yourself if you want to invoke SpamAssassin. Marc Merlin has written one for you: sa-exim. sa-exim invokes &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; in its &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; function and can thus take advantage of all of &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt;'s configuration options. This section describes the installation and configuration of sa-exim. You can download it at ''http://sa-exim.sf.net''. It requires Exim 4.11 or later.&lt;br /&gt;
&lt;br /&gt;
=== Buiding sa-exim for Static Integration ===&lt;br /&gt;
&lt;br /&gt;
Once you've unpacked the source code, you can choose one of two approaches to integrating sa-exim with Exim. This section focuses on ''static integration'', which embeds sa-exim within Exim at compile time. The examples in this section assume you have unpacked Exim's source code in ''/usr/local/src/exim-4.30'' and sa-exim's in ''/usr/local/src/sa-exim-3.1''.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;tip&amp;quot;&amp;gt;&lt;br /&gt;
'''Tip'''&lt;br /&gt;
&lt;br /&gt;
Whichever approach you choose for integrating sa-exim, be sure that &amp;lt;tt&amp;gt;LOCAL_SCAN_HAS_OPTIONS&amp;lt;/tt&amp;gt; has not been set to &amp;lt;tt&amp;gt;yes&amp;lt;/tt&amp;gt; in Exim's ''Local/Makefile'' (it is not set by default).&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To use the static integration approach, you edit sa-exim's ''sa-exim.c'' file, then replace Exim's ''src/local_scan.c'' file with sa-exim's ''sa-exim.c'' file, copy sa-exim's ''sa-exim.h'' file to the same location, and recompile (and reinstall) Exim. The &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; function in ''sa-exim.c'' replaces the default function.&lt;br /&gt;
&lt;br /&gt;
Two macro definitions in ''sa-exim.c'' must be edited. They appear in the code under the comment &amp;quot;Compile time config values&amp;quot; and provide the location of &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; (by default, ''/usr/bin/spamc'') and sa-exim's own configuration file (by default, ''/etc/exim4/sa-exim.conf'', but you might change this location to ''/usr/exim/sa-exim.conf'' or ''/etc/sa-exim.conf'' as suits your system).&lt;br /&gt;
&lt;br /&gt;
 $ '''cd /usr/local/src/sa-exim-3.1'''&lt;br /&gt;
 ...Edit sa-exim.c in your favorite editor...&lt;br /&gt;
 $ '''make sa-exim.h'''&lt;br /&gt;
 echo &amp;quot;char *version=\&amp;quot;`cat version` (built `date`)\&amp;quot;;&amp;quot; &amp;gt; sa-exim.h&lt;br /&gt;
 $ '''cp sa-exim.c ../exim-4.30/src/local_scan.c'''&lt;br /&gt;
 $ '''cp sa-exim.h ../exim-4.30/src'''&lt;br /&gt;
 $ '''cd ../exim-4.30'''&lt;br /&gt;
 $ '''make'''&lt;br /&gt;
 $ '''su'''&lt;br /&gt;
 Password: &lt;br /&gt;
 '''                  XXXXXXXX'''&lt;br /&gt;
 '''               '''&lt;br /&gt;
 # '''make install'''&lt;br /&gt;
             &lt;br /&gt;
&lt;br /&gt;
The static integration approach is easy but requires you to recompile Exim whenever you want to update sa-exim.&lt;br /&gt;
&lt;br /&gt;
=== Building sa-exim for Dynamic Integration ===&lt;br /&gt;
&lt;br /&gt;
Using the ''dynamic integration'' approach, you patch Exim to allow the &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; function to be dynamically loaded at runtime, and you compile sa-exim as a dynamically loadable executable. Many packaged versions of Exim are distributed with the dynamic loading patch already applied, but sa-exim includes two versions of the patches by David Woodhouse that you can apply to your Exim source code yourself. Use ''localscan_dlopen_up_to_4.14.patch'' to patch Exim versions 4.11 to 4.14; use ''localscan_dlopen_exim_4.20_or_better.patch'' to patch Exim 4.20 and later versions. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-10|Example 8-10]] illustrates the patch process.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-10&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-10. Patching Exim to support dynamic loading'''&lt;br /&gt;
&lt;br /&gt;
 $ '''cd /usr/local/src/exim-4.30'''&lt;br /&gt;
 $ '''patch -p1 &amp;lt; ../sa-exim-3.1/localscan_dlopen_exim_4.20_or_better.patch'''&lt;br /&gt;
 patching file src/EDITME&lt;br /&gt;
 Hunk #1 succeeded at 505 (offset 117 lines).&lt;br /&gt;
 patching file src/config.h.defaults&lt;br /&gt;
 Hunk #1 succeeded at 20 (offset 3 lines).&lt;br /&gt;
 patching file src/globals.c&lt;br /&gt;
 Hunk #1 succeeded at 108 (offset 5 lines).&lt;br /&gt;
 patching file src/globals.h&lt;br /&gt;
 Hunk #1 succeeded at 72 (offset 5 lines).&lt;br /&gt;
 patching file src/local_scan.c&lt;br /&gt;
 patching file src/readconf.c&lt;br /&gt;
 Hunk #1 succeeded at 224 (offset 42 lines).&lt;br /&gt;
 $ '''make'''&lt;br /&gt;
 $ '''su'''&lt;br /&gt;
 Password: &lt;br /&gt;
 '''                     XXXXXXXX'''&lt;br /&gt;
 '''                  '''&lt;br /&gt;
 # '''make install'''&lt;br /&gt;
                &lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
After installing the patched Exim, compile sa-exim as a dynamically loadable object file by editing its ''Makefile''. Check that the definitions of &amp;lt;tt&amp;gt;CC&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;CFLAGS&amp;lt;/tt&amp;gt;, and &amp;lt;tt&amp;gt;LDFLAGS&amp;lt;/tt&amp;gt; are suitable for building a shared object file with your compiler. Set the following macros in the''Makefile'':&lt;br /&gt;
&lt;br /&gt;
;&amp;lt;tt&amp;gt;SACONF&amp;lt;/tt&amp;gt;&lt;br /&gt;
: The path where you will locate sa-exim's configuration file (e.g., ''/etc/exim4/sa-exim.conf'', ''/usr/exim/sa-exim.conf'', or whatever suits your system)&lt;br /&gt;
;&amp;lt;tt&amp;gt;SPAMC&amp;lt;/tt&amp;gt;&lt;br /&gt;
: The location of &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; (e.g. ''/usr/bin/spamc'')&lt;br /&gt;
;&amp;lt;tt&amp;gt;EXIM_SRC&amp;lt;/tt&amp;gt;&lt;br /&gt;
: The path to the Exim source code's ''src'' directory (e.g., ''/usr/local/src/exim-4.30/''s''rc)''&lt;br /&gt;
&lt;br /&gt;
Run &amp;lt;tt&amp;gt;make&amp;lt;/tt&amp;gt; to compile sa-exim; &amp;lt;tt&amp;gt;make&amp;lt;/tt&amp;gt; should produce the shared object files ''sa-exim-3.1.so''and ''accept.so''. The former is the sa-exim replacement for the &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; function. The latter is a replacement for &amp;lt;tt&amp;gt;local_scan( )&amp;lt;/tt&amp;gt; that simply accepts all messages; you can use ''accept.so'' to test that dynamic loading works properly without the complexities of sa-exim.&lt;br /&gt;
&lt;br /&gt;
Copy these shared object files to an appropriate Exim directory (e.g., ''/usr/exim'' or ''/usr/exim/libexec''), and add the following lines to the beginning of Exim's configuration file:&lt;br /&gt;
&lt;br /&gt;
    local_scan_path = /usr/exim/accept.so&lt;br /&gt;
    #local_scan_path = /usr/exim/sa-exim-3.1.so&lt;br /&gt;
&lt;br /&gt;
Restart Exim, and confirm that messages are being received. After you finish configuring sa-exim, edit Exim's configuration file again, comment out the ''accept.so'' line, uncomment the ''sa-exim.so''line, and restart Exim again to activate sa-exim.&lt;br /&gt;
&lt;br /&gt;
=== Configuring SpamAssassin for sa-exim ===&lt;br /&gt;
&lt;br /&gt;
sa-exim invokes SpamAssassin using &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt;, so you must be running the &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; daemon to use sa-exim.&lt;br /&gt;
&lt;br /&gt;
sa-exim behaves as you'd expect with most of the settings you'd be likely to have in your sitewide configuration file (typically ''/etc/mail/spamassassin/local.cf''). One that requires particular care, however, is the &amp;lt;tt&amp;gt;report_safe&amp;lt;/tt&amp;gt; setting.&lt;br /&gt;
&lt;br /&gt;
If you set &amp;lt;tt&amp;gt;report_safe&amp;lt;/tt&amp;gt; to 0, SpamAssassin only adds spam-tagging headers and does not modify the body of messages. This setting works with sa-exim without any additional configuration and provides the fastest message-checking performance.&lt;br /&gt;
&lt;br /&gt;
If you prefer to have SpamAssassin modify the body of the message to add its report and convert the original message into an attachment, you can set &amp;lt;tt&amp;gt;report_safe&amp;lt;/tt&amp;gt; to 1 (include original message as ''message/rfc822'' attachment) or 2 (include original message as ''text/plain'' attachment). In this case, you have to set the &amp;lt;tt&amp;gt;SARewriteBody&amp;lt;/tt&amp;gt; variable in ''sa-exim.conf'' (described in the next section). Because sa-exim must read the modified body back from SpamAssassin, message-checking will be slightly slower than with &amp;lt;tt&amp;gt;report_safe&amp;lt;/tt&amp;gt; 0. In addition, if you perform message-archiving, the archives will contain the SpamAssassin-modified message.&lt;br /&gt;
&lt;br /&gt;
Finally, ensure that &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; is not being invoked with the &amp;lt;tt&amp;gt;--create-prefs&amp;lt;/tt&amp;gt; option, as it should run as an unprivileged user and be unable to create user preference files anyway. You may wish to include the &amp;lt;tt&amp;gt;--nouser-config&amp;lt;/tt&amp;gt; option as well.&lt;br /&gt;
&lt;br /&gt;
=== Configuring sa-exim ===&lt;br /&gt;
&lt;br /&gt;
You configure sa-exim by editing its ''sa-exim.conf'' configuration file. During the build of sa-exim, you should have specified a location for this file. Begin configuration by copying the ''sa-exim.conf'' file included with the sa-exim source code to this location. Edit the file to configure sa-exim.&lt;br /&gt;
&lt;br /&gt;
The ''sa-exim.conf'' file is copiously commented. As the first comment describes, sa-exim is picky about the formatting of options in this file. For example, the following are examples of valid options in ''sa-exim.conf'':&lt;br /&gt;
&lt;br /&gt;
 SApermreject: 12.0&lt;br /&gt;
 SARewriteBody: 0&lt;br /&gt;
 # The option below is commented out, and thus not set&lt;br /&gt;
 #SApermrejectsave: /var/spool/exim/SApermreject&lt;br /&gt;
&lt;br /&gt;
But none of this next set of options are valid:&lt;br /&gt;
&lt;br /&gt;
 # No spaces are allowed before the colon! One and only one is required after!&lt;br /&gt;
 Sapermreject :12.0&lt;br /&gt;
 # Only thresholds may be floating point numbers!&lt;br /&gt;
 SARewriteBody: 0.0&lt;br /&gt;
 # This sets the option, with an empty value! Not the way to unset it!&lt;br /&gt;
 SApermrejectsave:&lt;br /&gt;
&lt;br /&gt;
Later definitions of the same option override earlier ones.&lt;br /&gt;
&lt;br /&gt;
The configuration file determines how sa-exim handles spam: sa-exim can accept messages (returning a 2xx SMTP code), accept and discard messages, temporarily fail messages (returning a 4xx SMTP code), reject messages (returning a 5xx SMTP code), or perform teergrubing during the SMTP connection. For each sa-exim action, you can control at what spam threshold the action is triggered, whether a message that triggered the action should be saved to an archive directory, and the location of the archive directory. sa-exim usually names files in the archive directory by concatenating the time (in seconds since 00:00:00 UTC on January 1, 1970) and the value of the ''Message-ID'' header of a given message.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;sidebar&amp;quot;&amp;gt;&lt;br /&gt;
'''Teergrubing'''&lt;br /&gt;
&lt;br /&gt;
One interesting strategy that sa-exim provides for dealing with spam is ''teergrubing''. Teergrube is the German word for &amp;quot;tar pit,&amp;quot; and teergrubing is the practice of identifying spam while an SMTP connection is in progress and slowing down the SMTP connection. The goal is to tie up the spammers' mail server for as long as possible, reducing the rate at which they can spam.&lt;br /&gt;
&lt;br /&gt;
If you want to interfere with spammers' operations, sa-exim's teergrubing features may be for you. Note that you also tie up your own SMTP server processes while connections are maintained, but these processes will consume few resources as they'll primarily be sleeping.&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The following sections examine the options in the ''sa-exim.conf'' configuration file.&lt;br /&gt;
&lt;br /&gt;
==== Choosing messages on which to run SpamAssassin ====&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;SAEximRunCond&amp;lt;/tt&amp;gt; option specifies an Exim conditional expression that will be evaluated to determine whether SpamAssassin should be invoked on a message. To disable SpamAssassin, comment the option out or set its value to 0. To enable SpamAssassin on all messages, set the option's value to 1. The configuration file presents an example of how you can set this variable to check all messages except those originating from the local host or those with an ''X-SA-Do-Not-Run: Yes'' header:&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;SAEximRunCond: ${if and {{def:sender_host_address} {!eq {$sender_host_address}{127.0.&lt;br /&gt;
0.1}} {!eq {$h_X-SA-Do-Not-Run:}{Yes}} } {1}{0}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Choosing messages on which to take antispam actions ====&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;SAEximRejCond&amp;lt;/tt&amp;gt; option specifies an Exim conditional expression that will be evaluated to determine whether sa-exim should take actions on messages that SpamAssassin considers spam. By disabling the option, you can have messages checked by SpamAssassin (and tagged, if appropriate) but unconditionally accepted. The configuration file provides an example in which actions are taken on all spam messages except those with an ''X-SA-Do-Not-Rej: Yes'' header:&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;# X-SA-Do-Not-Rej should be set as a warn header if mail is sent to postmaster&lt;br /&gt;
# and abuse (in the RCPT ACL), this way you're not bouncing spam abuse reports&lt;br /&gt;
# sent to you&lt;br /&gt;
SAEximRejCond: ${if !eq {$h_X-SA-Do-Not-Rej:}{Yes} {1}{0}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The ''X-SA-Do-Not-Run'' and ''X-SA-Do-Not-Rej'' headers can be added by the &amp;lt;tt&amp;gt;acl_smtp_rcpt&amp;lt;/tt&amp;gt; ACL in Exim's own configuration file, using directives such as these:&lt;br /&gt;
&lt;br /&gt;
   warn     message       = X-SA-Do-Not-Run: Yes&lt;br /&gt;
            hosts         = +relay_from_hosts&lt;br /&gt;
 &lt;br /&gt;
   warn     message       = X-SA-Do-Not-Run: Yes&lt;br /&gt;
            authenticated = *&lt;br /&gt;
 &lt;br /&gt;
   warn     message       = X-SA-Do-Not-Rej: Yes&lt;br /&gt;
            local_parts   = postmaster:abuse&lt;br /&gt;
&lt;br /&gt;
These ACL directives will add ''X-SA-Do-Not-Run'' headers to messages from authenticated senders or from hosts from which Exim should relay messages, and will add ''X-SA-Do-Not-Rej'' headers to messages to ''postmaster'' or ''abuse''. The ''X-SA-Do-Not-Run'' header should be removed before messages are relayed to remote hosts; add a &amp;lt;tt&amp;gt;headers_remove&amp;lt;/tt&amp;gt; directive in the definition of the &amp;lt;tt&amp;gt;remote_smtp&amp;lt;/tt&amp;gt; transport:&lt;br /&gt;
&lt;br /&gt;
 remote_smtp:&lt;br /&gt;
   driver = smtp&lt;br /&gt;
   headers_remove = &amp;quot;X-SA-Do-Not-Run&amp;quot;&lt;br /&gt;
&lt;br /&gt;
You may wish to use different header names or values to prevent spammers from guessing your header and adding it to their spam messages to bypass sa-exim.&lt;br /&gt;
&lt;br /&gt;
==== Limiting how much of the message is fed to SpamAssassin ====&lt;br /&gt;
&lt;br /&gt;
&amp;lt;tt&amp;gt;SAmaxbody&amp;lt;/tt&amp;gt; determines how many bytes of a message body sa-exim will feed to SpamAssassin for checking; it defaults to 256,000. If &amp;lt;tt&amp;gt;SATruncBodyCond&amp;lt;/tt&amp;gt; evaluates to a false value, messages larger than &amp;lt;tt&amp;gt;SAmaxbody&amp;lt;/tt&amp;gt; are not scanned at all. If &amp;lt;tt&amp;gt;SATruncBodyCond&amp;lt;/tt&amp;gt; evaluates to a true value, such messages are truncated, and the first &amp;lt;tt&amp;gt;SAmaxbody&amp;lt;/tt&amp;gt; bytes are scanned. This is generally not a good idea because proper MIME message formatting requires a closing MIME boundary string at the end of a message, and if SpamAssassin receives a partial body missing this string, it may complain that the message is misformatted.&lt;br /&gt;
&lt;br /&gt;
==== Allowing SpamAssassin to rewrite message bodies ====&lt;br /&gt;
&lt;br /&gt;
If you set SpamAssassin's &amp;lt;tt&amp;gt;report_safe&amp;lt;/tt&amp;gt; option to 1 or 2 (asking SpamAssassin to rewrite message bodies), you must set the &amp;lt;tt&amp;gt;SARewriteBody&amp;lt;/tt&amp;gt; variable to 1.&lt;br /&gt;
&lt;br /&gt;
==== Archiving messages when actions are taken ====&lt;br /&gt;
&lt;br /&gt;
Archiving message bodies preserves copies of messages in case they are needed later, and archived messages can be used as a quarantine system.&lt;br /&gt;
&lt;br /&gt;
The value of &amp;lt;tt&amp;gt;SAmaxarchivebody&amp;lt;/tt&amp;gt; determines the amount of a message (in bytes) to save when archiving messages after taking action on them. It defaults to 20,971,520 (20MB), which is a reasonable value. Similarly, &amp;lt;tt&amp;gt;SAerrmaxarchivebody&amp;lt;/tt&amp;gt; determines the number of bytes of a message to save when a message causes an error in sa-exim. It defaults to 1,073,741,824 (1GB).&lt;br /&gt;
&lt;br /&gt;
If &amp;lt;tt&amp;gt;SAPrependArchiveWithFrom&amp;lt;/tt&amp;gt; is set to 1, sa-exim will add fake ''From'' lines to the beginning of archived messages so that the archive file will be in standard ''mbox'' format. This is usually desirable because it's easy to use most mail readers to examine an ''mbox'' file.&lt;br /&gt;
&lt;br /&gt;
==== Passing SMTP senders and recipients to SpamAssassin ====&lt;br /&gt;
&lt;br /&gt;
Because sa-exim is invoked at the end of the SMTP DATA step, it has access to the list of recipients provided in the SMTP RCPT commands from the sending MTA. If you set &amp;lt;tt&amp;gt;SAmaxrcptlength&amp;lt;/tt&amp;gt; to a value higher than 0, sa-exim adds an ''X-SA-Exim-Rcpt-To'' header containing the list of recipients as long as the list doesn't exceed the smaller of &amp;lt;tt&amp;gt;SAmaxrcptlength&amp;lt;/tt&amp;gt; bytes or 8 KB.&lt;br /&gt;
&lt;br /&gt;
sa-exim also has access to the SMTP MAIL FROM command and adds the SMTP sender to the message in the ''X-SA-Exim-Mail-From'' header&lt;br /&gt;
&lt;br /&gt;
The recipient list can be useful to SpamAssassin, as messages with a large number of recipients might be more likely to indicate spam, and the true list of recipients may not appear in the message ''To'' and ''Cc'' headers. Similarly, knowing the SMTP sender might help identify a known spammer or a spammer using an invalid sender address. By setting the &amp;lt;tt&amp;gt;SAaddSAEheaderBeforeSA&amp;lt;/tt&amp;gt; option to 1, you direct sa-exim to add these headers before invoking SpamAssassin on a message, which is the default. Set &amp;lt;tt&amp;gt;SAaddSAEheaderBeforeSA&amp;lt;/tt&amp;gt; to 0 if you prefer SpamAssassin to see messages with no sa-exim headers added.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;warning&amp;quot;&amp;gt;&lt;br /&gt;
'''Warning'''&lt;br /&gt;
&lt;br /&gt;
Adding the ''X-SA-Exim-Rcpt-To'' header will expose recipients who were blind carbon copied (Bcc) and foil other legitimate strategies to keep the list of message recipients private. You should remove this header in your message transports (using the &amp;lt;tt&amp;gt;remove_headers&amp;lt;/tt&amp;gt; directive) before messages are delivered.&lt;br /&gt;
&lt;br /&gt;
If you allow SpamAssassin to rewrite message bodies, however, the headers will be encapsulated in the body of spam messages and cannot be removed. This may be acceptable to you, as these messages are spam anyway, but the privacy risk in the case of a false positive should be considered.&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Setting a timeout on spamc ====&lt;br /&gt;
&lt;br /&gt;
sa-exim must wait for &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; to check messages but should not wait forever. By setting &amp;lt;tt&amp;gt;SAtimeout&amp;lt;/tt&amp;gt; to a value in seconds, you ensure that if &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; should fail to check a message in a reasonable time, the message will be accepted. If you set &amp;lt;tt&amp;gt;SAtimeout&amp;lt;/tt&amp;gt; to 0 (or to more than 300 seconds), Exim itself will interrupt a &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; run after five minutes, but it will cause the SMTP connection to return a temporary failure for the message, instead of accepting it. I recommend that you set &amp;lt;tt&amp;gt;SAtimeout&amp;lt;/tt&amp;gt; and use a value between 60 and 240 seconds.&lt;br /&gt;
&lt;br /&gt;
If a message is accepted due to a &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; timeout, and you set &amp;lt;tt&amp;gt;SAtimeoutsave&amp;lt;/tt&amp;gt; to the absolute path of a directory, the message will be saved in that directory so you can see the impact of your &amp;lt;tt&amp;gt;SAtimeout&amp;lt;/tt&amp;gt; settings. The directory must be writable by the Exim user; if it does not exist, sa-exim will attempt to create it.&lt;br /&gt;
&lt;br /&gt;
You can limit which of these messages are saved by defining &amp;lt;tt&amp;gt;SAtimeoutSavCond&amp;lt;/tt&amp;gt; to an Exim conditional expression. When &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; times out checking a message and the conditional expression returns a true value, the message will be saved. The default &amp;lt;tt&amp;gt;SAtimeoutSavCond&amp;lt;/tt&amp;gt; is 1, which saves all messages when &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt; times out.&lt;br /&gt;
&lt;br /&gt;
==== Handling messages that cause sa-exim errors ====&lt;br /&gt;
&lt;br /&gt;
Because sa-exim is a robust framework, it considers the possibility that a message might cause an error in sa-exim itself and provides the ability to handle such messages. If a message causes an error, and you set &amp;lt;tt&amp;gt;SAerrorsave&amp;lt;/tt&amp;gt; to the absolute path of a directory, the message will be saved in that directory. The directory must be writable by the Exim user; if it does not exist, sa-exim will attempt to create it.&lt;br /&gt;
&lt;br /&gt;
You can limit which error-causing messages are saved by defining &amp;lt;tt&amp;gt;SAerrorSavCond&amp;lt;/tt&amp;gt; to an Exim conditional expression. If an error occurs and the conditional expression returns a true value, the message will be saved. The default &amp;lt;tt&amp;gt;SAerrorSavCond&amp;lt;/tt&amp;gt; is 1, which saves all messages that cause sa-exim errors.&lt;br /&gt;
&lt;br /&gt;
By default, sa-exim will accept messages that cause errors, which prevents mail loss. An alternative is to have sa-exim instruct Exim to temporarily fail such messages, which will cause the sending MTA to queue them and retry delivery later. To temporarily fail messages that cause errors, set &amp;lt;tt&amp;gt;SAtemprejectonerror&amp;lt;/tt&amp;gt; to 1. Set the &amp;lt;tt&amp;gt;SAtemprejectonerror variable to&amp;lt;/tt&amp;gt; change the message that will be returned to the sending MTA when a message is temporarily failed by setting the &amp;lt;tt&amp;gt;SAmsgerror&amp;lt;/tt&amp;gt; variable.&lt;br /&gt;
&lt;br /&gt;
==== Teergrubing ====&lt;br /&gt;
&lt;br /&gt;
If you want sa-exim to perform teergrubing of a connection when spam is detected, set the &amp;lt;tt&amp;gt;SAteergrube&amp;lt;/tt&amp;gt; variable to the SpamAssassin spam score at or above which teergrubing should take place. If you don't define this variable, sa-exim will not teergrube. See the sidebar [[SpamAssassin/Integrating SpamAssassin with Exim|Teergrubing]], earlier in this chapter for an explanation of that technique.&lt;br /&gt;
&lt;br /&gt;
Set the &amp;lt;tt&amp;gt;SAteergrubcond&amp;lt;/tt&amp;gt; variable to an Exim conditional expression to determine whether teergrubing should be performed when the spam score exceeds the &amp;lt;tt&amp;gt;SAteergrube&amp;lt;/tt&amp;gt; threshold; teergrubing will be performed only when the expression evaluates to a true value. Use this variable to prevent teergrubing from affecting you or your secondary mail exchangers. The default ''sa-exim.conf'' file includes the following example, which prevents teergrubing of connections from 127.0.0.1 and 127.0.0.2:&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;SAteergrubecond: ${if and { {!eq {$sender_host_address}{127.0.0.1}} {!eq {$sender_&lt;br /&gt;
host_address}{127.0.0.2}} } {1}{0}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can configure the teergrube delay—the total amount of time, in seconds, that you want to try to tie up the sending MTA—by setting the &amp;lt;tt&amp;gt;SAteergrubetime&amp;lt;/tt&amp;gt; variable. The default is 900 (15 minutes). Every ten seconds during the teergrubing period, sa-exim will transmit SMTP code 451 with the reason given in &amp;lt;tt&amp;gt;SAmsgteergrubewait&amp;lt;/tt&amp;gt; (which defaults to &amp;quot;wait for more output&amp;quot;). At the end of the teergrubing period, sa-exim will temporarily fail the message with the reason given in &amp;lt;tt&amp;gt;SAmsgteergruberej&amp;lt;/tt&amp;gt; (which defaults to &amp;quot;Please try again later&amp;quot;). sa-exim temporarily fails the messages in the hopes that the sending MTA will later attempt to resend the message and spend more time in the tar pit.&lt;br /&gt;
&lt;br /&gt;
If a message qualifies a connection for teergrubing, and you set &amp;lt;tt&amp;gt;SAteergrubesave&amp;lt;/tt&amp;gt; to the absolute path of a directory, the message will be saved in that directory. The directory must be writable by the Exim user; if it does not exist, sa-exim will attempt to create it.&lt;br /&gt;
&lt;br /&gt;
You can limit which of these messages are saved by defining &amp;lt;tt&amp;gt;SAteergrubeSavCond&amp;lt;/tt&amp;gt; to an Exim conditional expression. If the conditional expression returns a true value, the message will be saved. The default &amp;lt;tt&amp;gt;SAteergrubeSavCond&amp;lt;/tt&amp;gt; is 1, which saves all messages that trigger teergrubing.&lt;br /&gt;
&lt;br /&gt;
Because sa-exim temporarily fails teergrubed mail after the teergrubing period, the sending MTA is likely to resend the same message. If you are saving messages that trigger teergrubing, it could lead to repeatedly saving multiple copies of the same message. To prevent this, set &amp;lt;tt&amp;gt;SAteergrubeoverwrite&amp;lt;/tt&amp;gt; to 1 (which is the default), and sa-exim will use only the message ID as the filename when saving teergrubed messages. Because resends should have the same message ID, this will result in a single copy of the message being kept, as older copies are overwritten by newer copies assigned the same filename.&lt;br /&gt;
&lt;br /&gt;
==== Accepting and discarding spam ====&lt;br /&gt;
&lt;br /&gt;
If you want sa-exim to accept and discard spam, set the &amp;lt;tt&amp;gt;SAdevnull&amp;lt;/tt&amp;gt; variable to the SpamAssassin spam score at or above which messages should be accepted and discarded. If you don't define this variable, sa-exim will not take those actions.&lt;br /&gt;
&lt;br /&gt;
If a message is to be discarded, and you set &amp;lt;tt&amp;gt;SAdevnullsave&amp;lt;/tt&amp;gt; to the absolute path of a directory, the message will be saved in that directory. The directory must be writable by the Exim user; if it does not exist, sa-exim will attempt to create it.&lt;br /&gt;
&lt;br /&gt;
You can limit which of these messages are saved by defining &amp;lt;tt&amp;gt;SAdevnullSavCond&amp;lt;/tt&amp;gt; to an Exim conditional expression. If the conditional expression returns a true value, the message will be saved. The default &amp;lt;tt&amp;gt;SAdevnullSavCond&amp;lt;/tt&amp;gt; is 1, which saves all messages that are discarded.&lt;br /&gt;
&lt;br /&gt;
==== Rejecting spam ====&lt;br /&gt;
&lt;br /&gt;
If you want sa-exim to reject spam during the SMTP connection, set the &amp;lt;tt&amp;gt;SApermreject&amp;lt;/tt&amp;gt; variable to the SpamAssassin spam score at or above which messages should be rejected. If you don't define this variable, sa-exim will not take this action. You can customize the rejection explanation that is sent along with the SMTP rejection code by setting &amp;lt;tt&amp;gt;SAmsgpermreject&amp;lt;/tt&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
If a message is to be rejected, and you set &amp;lt;tt&amp;gt;SApermrejectsave&amp;lt;/tt&amp;gt; to the absolute path of a directory, the message will be saved in that directory. The directory must be writable by the Exim user; if it does not exist, sa-exim will attempt to create it.&lt;br /&gt;
&lt;br /&gt;
You can limit which of these messages are saved by defining &amp;lt;tt&amp;gt;SApermrejectSavCond&amp;lt;/tt&amp;gt; to an Exim conditional expression. If the conditional expression returns a true value, the message will be saved. The default &amp;lt;tt&amp;gt;SApermrejectSavCond&amp;lt;/tt&amp;gt; is 1, which saves all messages that are rejected.&lt;br /&gt;
&lt;br /&gt;
==== Temporarily failing spam ====&lt;br /&gt;
&lt;br /&gt;
If you want sa-exim to temporarily fail spam during the SMTP connection, set the &amp;lt;tt&amp;gt;SAtempreject&amp;lt;/tt&amp;gt; variable to the SpamAssassin spam score at or above which messages should be temporarily failed. If you don't define this variable, sa-exim will not take this action. You can customize the rejection explanation that is sent along with the SMTP rejection code by setting &amp;lt;tt&amp;gt;SAmsgtempreject&amp;lt;/tt&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
If a message is to be temporarily failed, and you set &amp;lt;tt&amp;gt;SAtemprejectsave&amp;lt;/tt&amp;gt; to the absolute path of a directory, the message will be saved in that directory. The directory must be writable by the Exim user; if it does not exist, sa-exim will attempt to create it.&lt;br /&gt;
&lt;br /&gt;
You can limit which of these messages are saved by defining &amp;lt;tt&amp;gt;SAtempmrejectSavCond&amp;lt;/tt&amp;gt; to an Exim conditional expression. If the conditional expression returns a true value, the message will be saved. The default &amp;lt;tt&amp;gt;SAtemprejectSavCond&amp;lt;/tt&amp;gt; is 1, which saves all messages that are temporarily failed.&lt;br /&gt;
&lt;br /&gt;
When sa-exim temporarily fails a message, the sending MTA is likely to resend the same message. If you are saving messages that trigger temporary rejections, this could lead to repeatedly saving multiple copies of the same message. To prevent this, set &amp;lt;tt&amp;gt;SAtemprejectoverwrite&amp;lt;/tt&amp;gt; to 1 (which is the default), and sa-exim will use only the message ID as the filename when saving temporarily failed messages. Because resends should have the same message ID, this will result in single copies of messages being kept, as older copies are overwritten by newer copies assigned the same filename.&lt;br /&gt;
&lt;br /&gt;
There are few good reasons to temporarily fail spam. If you do not want to receive spam at all, permanently reject or accept and discard it instead. If you want to tie up spammer MTAs, teergrube instead. sa-exim includes temporary failing for completeness, but I do not recommend its use.&lt;br /&gt;
&lt;br /&gt;
==== Archiving accepted spam ====&lt;br /&gt;
&lt;br /&gt;
When sa-exim receives a message that SpamAssassin tags as spam but that does not meet any of the sa-exim action thresholds, sa-exim will accept the (tagged) message and allow it to be delivered to the recipient.&lt;br /&gt;
&lt;br /&gt;
If a message is to be accepted, and you set &amp;lt;tt&amp;gt;SAspamacceptsave&amp;lt;/tt&amp;gt; to the absolute path of a directory, the message will be saved in that directory. The directory must be writable by the Exim user; if it does not exist, sa-exim will attempt to create it.&lt;br /&gt;
&lt;br /&gt;
You can limit which of these messages are archived by defining &amp;lt;tt&amp;gt;SAspamacceptSavCond&amp;lt;/tt&amp;gt; to an Exim conditional expression. If the conditional expression returns a true value, a message will be archived. The default &amp;lt;tt&amp;gt;SAspamacceptSavCond&amp;lt;/tt&amp;gt; is 0, which does not archive any accepted spam messages.&lt;br /&gt;
&lt;br /&gt;
Although this feature is not useful for end users, mail administrators can use it to help decide whether to lower one of the other action thresholds by examining the saved messages. If there are no false positives, you might lower the action thresholds.&lt;br /&gt;
&lt;br /&gt;
==== Archiving non-spam messages ====&lt;br /&gt;
&lt;br /&gt;
When sa-exim receives a message that SpamAssassin does not consider spam, sa-exim will (of course) accept the message and allow it to be delivered to the recipient.&lt;br /&gt;
&lt;br /&gt;
If a non-spam message is received, and you set &amp;lt;tt&amp;gt;SAnotspamsave&amp;lt;/tt&amp;gt; to the absolute path of a directory, the message will be saved in that directory. The directory must be writable by the Exim user; if it does not exist, sa-exim will attempt to create it.&lt;br /&gt;
&lt;br /&gt;
You can limit which of these messages are saved by defining &amp;lt;tt&amp;gt;SAnotspamSavCond&amp;lt;/tt&amp;gt; to an Exim conditional expression. If the conditional expression returns a true value, the message will be saved. The default &amp;lt;tt&amp;gt;SAnotspamSavCond&amp;lt;/tt&amp;gt; is 0, which does not save any accepted non-spam messages.&lt;br /&gt;
&lt;br /&gt;
A mail administrator might use this feature to analyze a group of non-spam messages to determine whether SpamAssassin is making too many false negative judgments, but on a busy mail site, saving extra copies of all legitimate incoming mail is probably not a good idea. sa-exim includes this feature primarily for completeness.&lt;br /&gt;
&lt;br /&gt;
==== Debugging sa-exim ====&lt;br /&gt;
&lt;br /&gt;
Set the &amp;lt;tt&amp;gt;SAEximDebug&amp;lt;/tt&amp;gt; variable to a number between 1 and 9 to enable extra logging; higher numbers produce more debugging output. The distributed ''sa-exim.conf'' file sets this variable to 1, which will log a notice whenever sa-exim saves a new message to one of its archive directories, invokes &amp;lt;tt&amp;gt;spamc&amp;lt;/tt&amp;gt;, rewrites message bodies, or evaluates an Exim conditional expression. Increasing &amp;lt;tt&amp;gt;SAEximDebug&amp;lt;/tt&amp;gt; is a good idea, particularly when testing new conditional expressions.&lt;br /&gt;
&lt;br /&gt;
[[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-11|Example 8-11]] shows a complete ''sa-exim.conf'' file (without comments). In this example, sa-exim is configured to reject (but save) messages with spam scores higher than 15.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-11&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-11. A complete sa-exim.conf file'''&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;# Run SpamAssassin unless the message was submitted locally or the&lt;br /&gt;
# X-SA-Do-Not-Run header is set to 'secret'. We configure Exim elsewhere&lt;br /&gt;
# to set this header for messages from authenticated senders or hosts&lt;br /&gt;
# we relay for&lt;br /&gt;
SAEximRunCond: ${if and {{def:sender_host_address} {!eq {$sender_host_address}{127.0.0.&lt;br /&gt;
1}} {!eq {$h_X-SA-Do-Not-Run:}{secret}} } {1}{0}}&lt;br /&gt;
&lt;br /&gt;
# Don't take action on messages if X-SpamAssassin-Do-Not-Rej header is set to&lt;br /&gt;
# 'secret'. We configure Exim to set this header for messages to the postmaster.&lt;br /&gt;
SAEximRejCond: ${if !eq {$h_X-SA-Do-Not-Rej:}{Yes} {1}{0}}&lt;br /&gt;
&lt;br /&gt;
# Feed up to 300Kb to SpamAssassin, and if the message is longer, don't&lt;br /&gt;
# bother spam checkign&lt;br /&gt;
SAmaxbody: 307200&lt;br /&gt;
SATruncBodyCond: 0&lt;br /&gt;
&lt;br /&gt;
# We don't let SpamAssassin rewrite message bodies, so we don't set this&lt;br /&gt;
SARewriteBody: 0&lt;br /&gt;
&lt;br /&gt;
# I prefer to avoid the X-SA-Exim-Rcpt-To header, for privacy reasons.&lt;br /&gt;
SAmaxrcptlistlength: 0&lt;br /&gt;
&lt;br /&gt;
# Allow spamc 2 minutes for each message. If it times out, don't bother &lt;br /&gt;
# saving messages, just accept them.&lt;br /&gt;
SAtimeout: 120&lt;br /&gt;
SAtimeoutsave:&lt;br /&gt;
SAtimeoutSavCond: 0&lt;br /&gt;
&lt;br /&gt;
# Do save messages that cause an error in sa-exim, but accept them&lt;br /&gt;
SAerrorsave: /var/spool/exim/SAerrorsave&lt;br /&gt;
SAerrorSavCond: 1&lt;br /&gt;
SAtemprejectonerror: 0&lt;br /&gt;
&lt;br /&gt;
# Reject messages with SpamAssassin scores of 15 or higher, but save a&lt;br /&gt;
# copy of them.&lt;br /&gt;
SApermreject: 15.0&lt;br /&gt;
SApermrejectSavCond: 1&lt;br /&gt;
SApermrejectsave: /var/spool/exim/SApermreject&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Using Per-User Preferences ===&lt;br /&gt;
&lt;br /&gt;
Like exiscan, sa-exim checks messages for spam just once—at message receipt after the SMTP DATA command. And like exiscan, it's difficult to use SpamAssassin's per-user preference files with sa-exim. Messages may have multiple recipients, some of whom are not local, and sa-exim will not be able to determine whose preferences should be used.&lt;br /&gt;
&lt;br /&gt;
You can use per-user preferences with sa-exim in the same ways as you can with exiscan, and with the same performance costs:&lt;br /&gt;
&lt;br /&gt;
* You can ensure that each email message will have only a single recipient by writing an ACL for the SMTP RCPT TO phase that defers all recipients except the first one. The sending MTA will retry delivery to the deferred recipients but may not do so immediately. As a result, some copies of messages with multiple recipients may be significantly delayed.&lt;br /&gt;
* You can use sa-exim to perform initial spam-checking and refuse messages with high scores, and then use the router/transport approach described earlier to reinvoke SpamAssassin on the remaining messages for local recipients. This approach results in an extra &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; connection for each message with a local recipient but might be worthwhile if sa-exim can refuse enough very obvious spam sent to multiple recipients.&lt;br /&gt;
&lt;br /&gt;
== Building a Spam-Checking Gateway ==&lt;br /&gt;
&lt;br /&gt;
Any of the approaches discussed earlier can form the basis for a spam-checking Exim gateway. exiscan or sa-exim will likely yield better performance than a router/transport approach, and I recommend using them unless you need per-user preferences and are prepared to configure &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; to perform SQL-based lookups. The remainder of this chapter explains how to configure an Exim-based gateway for routing messages and how to add sitewide Bayesian filtering and autowhitelisting.&lt;br /&gt;
&lt;br /&gt;
=== Routing Email Through the Gateway ===&lt;br /&gt;
&lt;br /&gt;
Once you have Exim receiving messages for the local host and performing SpamAssassin checks on them using any of the methods outlined earlier, you can start accepting email for your domain and routing it to an internal mail server after spam-checking. [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-FIG-5|Figure 8-5]] illustrates this topology.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-FIG-5&amp;quot;&amp;gt;&lt;br /&gt;
'''Figure 8-5. Spam-checking gateway topology'''&lt;br /&gt;
&lt;br /&gt;
[[Image:SpamAssassin_I_8_tt159.png|Spam-checking gateway topology]]&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Exim domain lists ====&lt;br /&gt;
&lt;br /&gt;
To configure Exim to relay incoming mail for ''example.com'' to ''internal.example.com'', add the following lines to Exim's configuration file:&lt;br /&gt;
&lt;br /&gt;
 domainlist local_domains = @&lt;br /&gt;
 domainlist relay_to_domains = example.com&lt;br /&gt;
&lt;br /&gt;
The key feature of this configuration is that ''example.com'' is a domain to which Exim may relay but is not on the list of local domains (for which mail is to be delivered on this host). Remember that you must restart Exim after changing its configuration file.&lt;br /&gt;
&lt;br /&gt;
==== Routing changes ====&lt;br /&gt;
&lt;br /&gt;
Mail from the Internet for ''example.com'' should be sent to the spam-checking gateway ''mail.example.com''. Add a DNS MX record for the ''example.com'' domain that points to ''mail.example.com''.&lt;br /&gt;
&lt;br /&gt;
Once received by ''mail.example.com'', messages will be spam-checked and should then be relayed to ''internal.example.com'' by Exim. There are two ways to get Exim to relay these messages:&lt;br /&gt;
&lt;br /&gt;
* Set up an internal DNS MX record for ''example.com'' pointing to ''internal.example.com''. When Exim on ''mail.example.com'' attempts to deliver messages for ''example.com'', the &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt; router will look up this MX record and deliver the messages to the internal mail host. This configuration may require that you run a &amp;quot;split DNS&amp;quot; system or use BIND 9's views feature to ensure that different MX records for ''example.com'' are published to the Internet and to internal hosts.&lt;br /&gt;
* Set up a new Exim router using the &amp;lt;tt&amp;gt;manualroute&amp;lt;/tt&amp;gt; driver to manually route incoming messages for ''example.com'' to the internal mail host. The router definition, shown in [[SpamAssassin/Integrating SpamAssassin with Exim#spamassassin-CHP-8-EX-12|Example 8-12]], should be placed in the list of routers before the &amp;lt;tt&amp;gt;dnslookup&amp;lt;/tt&amp;gt; router. In this case, ''mail.example.com'' need only be able to resolve ''internal.example.com'' (or the IP address for ''internal.example.com'' could be substituted for its name in the router definition).&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div id=&amp;quot;spamassassin-CHP-8-EX-12&amp;quot;&amp;gt;&lt;br /&gt;
'''Example 8-12. Using a manualroute router to relay messages'''&lt;br /&gt;
&lt;br /&gt;
 internal_relay:&lt;br /&gt;
   driver = manualroute&lt;br /&gt;
   domains = example.com&lt;br /&gt;
   transport = remote_smtp&lt;br /&gt;
   route_list = example.com internal.example.com&lt;br /&gt;
&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Internal server configuration ====&lt;br /&gt;
&lt;br /&gt;
Once the external mail gateway is in place, you can configure the internal mail server to accept only SMTP connections from the gateway (for incoming Internet mail). If you don't have a separate server for outgoing mail, the internal mail server should also accept SMTP connections from hosts on the internal network. These restrictions are usually enforced by limiting access to TCP port 25 using a host-based firewall or a packet-filtering router.&lt;br /&gt;
&lt;br /&gt;
=== Adding Sitewide Bayesian Filtering ===&lt;br /&gt;
&lt;br /&gt;
You can easily add sitewide Bayesian filtering to any of the Exim approaches because they are all based on &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt;. Use the usual SpamAssassin &amp;lt;tt&amp;gt;use_bayes&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;bayes_path&amp;lt;/tt&amp;gt; directives in ''local.cf'', and ensure that &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; has permission to create the databases in the directory named in &amp;lt;tt&amp;gt;bayes_path&amp;lt;/tt&amp;gt;. Use a directory for the databases that is owned by &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt;'s user, such as ''/var/spamd''(or perhaps use ''/etc/mail/spamassassin''). If local users need access to the databases (e.g., they will be running &amp;lt;tt&amp;gt;sa-learn)&amp;lt;/tt&amp;gt;, you may have to make the databases readable or writable by a group other than &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt;'s and adjust &amp;lt;tt&amp;gt;bayes_file_mode&amp;lt;/tt&amp;gt;. Or you can make the databases world-readable or world-writable. Doing so, however, is unlikely to be necessary on a gateway system and puts the integrity of your spam-checking at the mercy of the good intentions and comprehension of your users.&lt;br /&gt;
&lt;br /&gt;
=== Adding Sitewide Autowhitelisting ===&lt;br /&gt;
&lt;br /&gt;
Adding sitewide autowhitelisting is very similar to adding a sitewide Bayesian database. Just add the usual SpamAssassin &amp;lt;tt&amp;gt;auto_whitelist_path&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;auto_whitelist_file_mode&amp;lt;/tt&amp;gt; directives to ''local.cf''. As with the Bayesian databases, &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt;'s user must have permission to create the autowhitelist database and read and write to it. In SpamAssassin 2.6x, &amp;lt;tt&amp;gt;spamd&amp;lt;/tt&amp;gt; must be started with the &amp;lt;tt&amp;gt;--auto-whitelist&amp;lt;/tt&amp;gt; option; this option is not needed (and is deprecated) in SpamAssassin 3.0 .&lt;/div&gt;</summary>
		<author><name>Docbook2Wiki</name></author>	</entry>

	</feed>