Make the multi_domain smtp transport option expanded
authorJeremy Harris <jgh146exb@wizmail.org>
Sun, 16 Nov 2014 17:47:50 +0000 (17:47 +0000)
committerJeremy Harris <jgh146exb@wizmail.org>
Mon, 12 Jan 2015 18:58:33 +0000 (18:58 +0000)
doc/doc-docbook/spec.xfpt
doc/doc-txt/ChangeLog
src/src/deliver.c
src/src/globals.c
src/src/structs.h
src/src/transports/smtp.c
test/confs/0570 [new file with mode: 0644]
test/log/0570 [new file with mode: 0644]
test/rejectlog/0570 [new file with mode: 0644]
test/scripts/0000-Basic/0570 [new file with mode: 0644]

index c6aeea145db4f67e292299c92129bca5cbdf751c..0047f6bde7d00b500febf939d308ee6eb6ac076f 100644 (file)
@@ -23224,7 +23224,7 @@ so can cause parallel connections to the same host if &%remote_max_parallel%&
 permits this.
 
 
-.option multi_domain smtp boolean true
+.option multi_domain smtp boolean&!! true
 .vindex "&$domain$&"
 When this option is set, the &(smtp)& transport can handle a number of
 addresses containing a mixture of different domains provided they all resolve
@@ -23233,6 +23233,9 @@ handling only one domain at a time. This is useful if you want to use
 &$domain$& in an expansion for the transport, because it is set only when there
 is a single domain involved in a remote delivery.
 
+It is expanded per-address and can depend on any of
+&$address_data$&, &$domain_data$&, &$local_part_data$&,
+&$host$&, &$host_address$& and &$host_port$&.
 
 .option port smtp string&!! "see below"
 .cindex "port" "sending TCP/IP"
index ae2b84dd079c6c576256c34d4636f9b14aab18b6..768d872e197905a07db1f8578ea31d3fb8687eb6 100644 (file)
@@ -7,6 +7,8 @@ Exim version 4.86
 JH/01 Bug 1545: The smtp transport option "retry_include_ip_address" is now
       expanded.
 
+JH/02 The smtp transport option "multi_domain" is now expanded.
+
 
 Exim version 4.85
 -----------------
index d33cf799ab652a3a13b18c3133f4cbf84d18fa01..5000f1cbc38a22b2f408c3798c0b1cfd431d5e92 100644 (file)
@@ -3844,9 +3844,20 @@ for (delivery_count = 0; addr_remote != NULL; delivery_count++)
     }
 
   /* Get the flag which specifies whether the transport can handle different
-  domains that nevertheless resolve to the same set of hosts. */
-
-  multi_domain = tp->multi_domain;
+  domains that nevertheless resolve to the same set of hosts. If it needs
+  expanding, get variables set: $address_data, $domain_data, $localpart_data,
+  $host, $host_address, $host_port. */
+  if (tp->expand_multi_domain)
+    deliver_set_expansions(addr);
+
+  if (exp_bool(addr, US"transport", tp->name, D_transport,
+               US"multi_domain", tp->multi_domain, tp->expand_multi_domain,
+               &multi_domain) != OK)
+    {
+    deliver_set_expansions(NULL);
+    remote_post_process(addr, LOG_MAIN|LOG_PANIC, addr->message, fallback);
+    continue;
+    }
 
   /* Get the maximum it can handle in one envelope, with zero meaning
   unlimited, which is forced for the MUA wrapper case. */
@@ -3915,26 +3926,35 @@ for (delivery_count = 0; addr_remote != NULL; delivery_count++)
   entirely different domains. The host list pointers can be NULL in the case
   where the hosts are defined in the transport. There is also a configured
   maximum limit of addresses that can be handled at once (see comments above
-  for how it is computed). */
+  for how it is computed).
+  If the transport does not handle multiple domains, enforce that also,
+  and if it might need a per-address check for this, re-evaluate it.
+  */
 
   while ((next = *anchor) != NULL && address_count < address_count_max)
     {
-    if ((multi_domain || Ustrcmp(next->domain, addr->domain) == 0)
-        &&
-        tp == next->transport
-        &&
-        same_hosts(next->host_list, addr->host_list)
-        &&
-        same_strings(next->p.errors_address, addr->p.errors_address)
-        &&
-        same_headers(next->p.extra_headers, addr->p.extra_headers)
-        &&
-        same_ugid(tp, next, addr)
-        &&
-        (next->p.remove_headers == addr->p.remove_headers ||
-          (next->p.remove_headers != NULL &&
-           addr->p.remove_headers != NULL &&
-           Ustrcmp(next->p.remove_headers, addr->p.remove_headers) == 0)))
+    BOOL md;
+    if (  (multi_domain || Ustrcmp(next->domain, addr->domain) == 0)
+       && tp == next->transport
+       && same_hosts(next->host_list, addr->host_list)
+       && same_strings(next->p.errors_address, addr->p.errors_address)
+       && same_headers(next->p.extra_headers, addr->p.extra_headers)
+       && same_ugid(tp, next, addr)
+       && (  next->p.remove_headers == addr->p.remove_headers
+         || (  next->p.remove_headers != NULL
+            && addr->p.remove_headers != NULL
+            && Ustrcmp(next->p.remove_headers, addr->p.remove_headers) == 0
+         )  )
+       && (  !multi_domain
+         || (  (
+               !tp->expand_multi_domain || (deliver_set_expansions(next), 1),
+               exp_bool(addr,
+                   US"transport", next->transport->name, D_transport,
+                   US"multi_domain", next->transport->multi_domain,
+                   next->transport->expand_multi_domain, &md) == OK
+               )
+            && md
+       )  )  )
       {
       *anchor = next->next;
       next->next = NULL;
@@ -3944,6 +3964,7 @@ for (delivery_count = 0; addr_remote != NULL; delivery_count++)
       address_count++;
       }
     else anchor = &(next->next);
+    deliver_set_expansions(NULL);
     }
 
   /* If we are acting as an MUA wrapper, all addresses must go in a single
index fb705d9d8a550cf01d2f8e368143f933cb3d78ba..f7c67d76f4d864b76babdc307d42be7484ee373f 100644 (file)
@@ -1356,6 +1356,7 @@ transport_instance  transport_defaults = {
     NULL,                     /* batch_id */
     NULL,                     /* home_dir */
     NULL,                     /* current_dir */
+    NULL,                     /* expand-multi-domain */
     TRUE,                     /* multi-domain */
     FALSE,                    /* overrides_hosts */
     100,                      /* max_addresses */
index 259d9af719183f60ee4a3ee119364832d7636908..2250bbbded5ccce4d0547b02cf2ff334818d96c8 100644 (file)
@@ -148,6 +148,7 @@ typedef struct transport_instance {
   uschar *home_dir;               /* ) Used only for local transports   */
   uschar *current_dir;            /* )                                  */
                                   /**************************************/
+  uschar *expand_multi_domain;    /* )                                  */
   BOOL    multi_domain;           /* )                                  */
   BOOL    overrides_hosts;        /* ) Used only for remote transports  */
   int     max_addresses;          /* )                                  */
index 33d357f7a17a3c0294e365bb795c2001fe2d6196..69bbc4d0c8df1295907f5b9dc0572bffa01d5865 100644 (file)
@@ -19,6 +19,8 @@ before the lower case letters). Some live in the transport_instance block so as
 to be publicly visible; these are flagged with opt_public. */
 
 optionlist smtp_transport_options[] = {
+  { "*expand_multi_domain",             opt_stringptr | opt_hidden | opt_public,
+      (void *)offsetof(transport_instance, expand_multi_domain) },
   { "*expand_retry_include_ip_address", opt_stringptr | opt_hidden,
        (void *)(offsetof(smtp_transport_options_block, expand_retry_include_ip_address)) },
 
@@ -145,7 +147,7 @@ optionlist smtp_transport_options[] = {
       (void *)offsetof(smtp_transport_options_block, lmtp_ignore_quota) },
   { "max_rcpt",             opt_int | opt_public,
       (void *)offsetof(transport_instance, max_addresses) },
-  { "multi_domain",         opt_bool | opt_public,
+  { "multi_domain",         opt_expand_bool | opt_public,
       (void *)offsetof(transport_instance, multi_domain) },
   { "port",                 opt_stringptr,
       (void *)offsetof(smtp_transport_options_block, port) },
diff --git a/test/confs/0570 b/test/confs/0570
new file mode 100644 (file)
index 0000000..4c5e5dc
--- /dev/null
@@ -0,0 +1,45 @@
+# Exim test configuration 0570
+# multi_domain option on smtp transport
+
+OPTION =
+
+exim_path = EXIM_PATH
+host_lookup_order = bydns
+rfc1413_query_timeout = 0s
+spool_directory = DIR/spool
+log_file_path = DIR/spool/log/%slog
+gecos_pattern = ""
+gecos_name = CALLER_NAME
+
+# ----- Main settings -----
+
+primary_hostname = primary.test.ex
+qualify_domain = test.ex
+queue_only
+queue_run_in_order
+
+
+# for server
+acl_smtp_rcpt= discard
+
+# ----- Routers -----
+
+begin routers
+
+all:
+  driver = manualroute
+address_data = $domain
+  route_list = *       127.0.0.1         byname
+  self = send
+  transport = smtp
+
+# ----- Transports -----
+
+begin transports
+
+smtp:
+  driver = smtp
+  port = PORT_D
+  OPTION
+
+# End
diff --git a/test/log/0570 b/test/log/0570
new file mode 100644 (file)
index 0000000..53ba80a
--- /dev/null
@@ -0,0 +1,83 @@
+1999-03-02 09:44:33 exim x.yz daemon started: pid=pppp, no queue runs, listening for SMTP on port 1225
+1999-03-02 09:44:33 10HmaX-0005vi-00 <= CALLER@test.ex U=CALLER P=local S=sss
+1999-03-02 09:44:33 Start queue run: pid=pppp
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmaY-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmaX-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmaY-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmaY-0005vi-00 Completed
+1999-03-02 09:44:33 10HmaX-0005vi-00 => userx@doma.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmaY-0005vi-00"
+1999-03-02 09:44:33 10HmaX-0005vi-00 -> usery@domb.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmaY-0005vi-00"
+1999-03-02 09:44:33 10HmaX-0005vi-00 Completed
+1999-03-02 09:44:33 End queue run: pid=pppp
+1999-03-02 09:44:33 10HmaZ-0005vi-00 <= CALLER@test.ex U=CALLER P=local S=sss
+1999-03-02 09:44:33 Start queue run: pid=pppp
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbA-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmaZ-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbA-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbA-0005vi-00 Completed
+1999-03-02 09:44:33 10HmaZ-0005vi-00 => userx@doma.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbA-0005vi-00"
+1999-03-02 09:44:33 10HmaZ-0005vi-00 -> usery@domb.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbA-0005vi-00"
+1999-03-02 09:44:33 10HmaZ-0005vi-00 Completed
+1999-03-02 09:44:33 End queue run: pid=pppp
+1999-03-02 09:44:33 10HmbB-0005vi-00 <= CALLER@test.ex U=CALLER P=local S=sss
+1999-03-02 09:44:33 Start queue run: pid=pppp
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbC-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmbB-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbC-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbC-0005vi-00 Completed
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbD-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmbB-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbD-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbD-0005vi-00 Completed
+1999-03-02 09:44:33 10HmbB-0005vi-00 => userx@doma.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbC-0005vi-00"
+1999-03-02 09:44:33 10HmbB-0005vi-00 => usery@domb.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbD-0005vi-00"
+1999-03-02 09:44:33 10HmbB-0005vi-00 Completed
+1999-03-02 09:44:33 End queue run: pid=pppp
+1999-03-02 09:44:33 Start queue run: pid=pppp
+1999-03-02 09:44:33 End queue run: pid=pppp
+1999-03-02 09:44:33 10HmbE-0005vi-00 <= CALLER@test.ex U=CALLER P=local S=sss
+1999-03-02 09:44:33 Start queue run: pid=pppp
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbF-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmbE-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbF-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbF-0005vi-00 Completed
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbG-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmbE-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbG-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbG-0005vi-00 Completed
+1999-03-02 09:44:33 10HmbE-0005vi-00 => userx@doma.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbF-0005vi-00"
+1999-03-02 09:44:33 10HmbE-0005vi-00 => usery@domb.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbG-0005vi-00"
+1999-03-02 09:44:33 10HmbE-0005vi-00 Completed
+1999-03-02 09:44:33 End queue run: pid=pppp
+1999-03-02 09:44:33 10HmbH-0005vi-00 <= CALLER@test.ex U=CALLER P=local S=sss
+1999-03-02 09:44:33 Start queue run: pid=pppp
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbI-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmbH-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbI-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbI-0005vi-00 Completed
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbJ-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmbH-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbJ-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbJ-0005vi-00 Completed
+1999-03-02 09:44:33 10HmbH-0005vi-00 => userx@doma.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbI-0005vi-00"
+1999-03-02 09:44:33 10HmbH-0005vi-00 => usery@domb.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbJ-0005vi-00"
+1999-03-02 09:44:33 10HmbH-0005vi-00 Completed
+1999-03-02 09:44:33 End queue run: pid=pppp
+1999-03-02 09:44:33 10HmbK-0005vi-00 <= CALLER@test.ex U=CALLER P=local S=sss
+1999-03-02 09:44:33 Start queue run: pid=pppp
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbL-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmbK-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbL-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbL-0005vi-00 Completed
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userz@domC.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 10HmbM-0005vi-00 <= CALLER@test.ex H=localhost (primary.test.ex) [127.0.0.1] P=esmtp S=sss id=E10HmbK-0005vi-00@primary.test.ex
+1999-03-02 09:44:33 10HmbM-0005vi-00 => blackhole (RCPT ACL discarded recipients)
+1999-03-02 09:44:33 10HmbM-0005vi-00 Completed
+1999-03-02 09:44:33 10HmbK-0005vi-00 => userx@doma.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbL-0005vi-00"
+1999-03-02 09:44:33 10HmbK-0005vi-00 -> usery@doma.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbL-0005vi-00"
+1999-03-02 09:44:33 10HmbK-0005vi-00 => userz@domc.ex R=all T=smtp H=127.0.0.1 [127.0.0.1] C="250 OK id=10HmbM-0005vi-00"
+1999-03-02 09:44:33 10HmbK-0005vi-00 Completed
+1999-03-02 09:44:33 End queue run: pid=pppp
diff --git a/test/rejectlog/0570 b/test/rejectlog/0570
new file mode 100644 (file)
index 0000000..d179df7
--- /dev/null
@@ -0,0 +1,13 @@
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domB.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userx@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <usery@domA.ex>: discarded by RCPT ACL
+1999-03-02 09:44:33 H=localhost (primary.test.ex) [127.0.0.1] F=<CALLER@test.ex> rejected RCPT <userz@domC.ex>: discarded by RCPT ACL
diff --git a/test/scripts/0000-Basic/0570 b/test/scripts/0000-Basic/0570
new file mode 100644 (file)
index 0000000..ed54afc
--- /dev/null
@@ -0,0 +1,66 @@
+# multi_domain option on smtp transport
+#
+#
+exim -DSERVER=server -bd -oX PORT_D
+****
+#
+exim userx@domA.ex usery@domB.ex
+Test message
+****
+# Default case: can multi-domain
+exim -q
+****
+#
+#
+exim userx@domA.ex usery@domB.ex
+Test message
+****
+# Equivalent explicit case: can multi-domain
+exim -DOPTION=multi_domain=yes -q
+****
+#
+#
+exim userx@domA.ex usery@domB.ex
+Test message
+****
+# no multi-domain
+exim -DOPTION=multi_domain=no -q
+#
+#
+exim userx@domA.ex usery@domB.ex
+Test message
+****
+# Expanded case: can multi-domain
+exim -DOPTION='multi_domain=${if bool{1} {true}{false}}' -q
+****
+#
+#
+exim userx@domA.ex usery@domB.ex
+Test message
+****
+# Expanded case: no multi-domain (1)
+exim -DOPTION='multi_domain=${if eqi {$address_data}{domA.ex} {no}{yes}}' -q
+****
+#
+#
+exim userx@domA.ex usery@domB.ex
+Test message
+****
+# Expanded case: no multi-domain (2)
+exim -DOPTION='multi_domain=${if match_domain {$address_data}{domZ.ex : domY.ex : domB.ex} {no}{yes}}' -q
+****
+#
+#
+exim userx@domA.ex usery@domA.ex userz@domC.ex
+Test message
+****
+# Expanded case: both yes and no
+exim -DOPTION='multi_domain=${if eqi {$address_data}{domA.ex} {no}{yes}}' -q
+****
+#
+#
+killdaemon
+no_msglog_check
+#
+#
+##