chiark / gitweb /
Merge branch 'mdw/relayhosts'
authorMark Wooding <mdw@distorted.org.uk>
Tue, 14 Feb 2006 02:52:33 +0000 (02:52 +0000)
committerMark Wooding <mdw@distorted.org.uk>
Tue, 14 Feb 2006 02:52:33 +0000 (02:52 +0000)
* mdw/relayhosts:
  qmail-smtpd: Read list of hosts allowed to relay from control/relayhosts

Conflicts:

qmail-control.9
qmail-showctl.c
qmail-smtpd.c

qmail-control.9
qmail-showctl.c
qmail-smtpd.8
qmail-smtpd.c

index 503ce93659ae756e2369760e732587e2e909fc83..c31050d469799c378ce08b0ab775b85817f92284 100644 (file)
@@ -61,6 +61,7 @@ control       default used by
 .I qmqpservers \fR(none)       \fRqmail-qmqpc
 .I queuelifetime       \fR604800       \fRqmail-send
 .I rcpthosts   \fR(none)       \fRqmail-smtpd
+.I relayhosts  \fR(none)       \fRqmail-smtpd
 .I smtpgreeting        \fIme   \fRqmail-smtpd
 .I smtproutes  \fR(none)       \fRqmail-remote
 .I timeoutconnect      \fR60   \fRqmail-remote
index a24aa63eccc147e7d73a25b1f714551967f5785c..5886ab147e283570f33483b42d5f35cd23db1d5a 100644 (file)
@@ -255,6 +255,7 @@ void main()
       else
         substdio_puts(subfdout,"Modified recently enough; hopefully up to date.\n");
 
+  do_lst("relayhosts","No relayhosts","Relay host: ","");
   do_str("smtpgreeting",1,"smtpgreeting","SMTP greeting: 220 ");
   do_lst("smtproutes","No artificial SMTP routes.","SMTP route: ","");
   do_int("timeoutconnect","60","SMTP client connection timeout is "," seconds");
@@ -290,6 +291,7 @@ void main()
     if (str_equal(d->d_name,"qmqpservers")) continue;
     if (str_equal(d->d_name,"queuelifetime")) continue;
     if (str_equal(d->d_name,"rcpthosts")) continue;
+    if (str_equal(d->d_name,"relayhosts")) continue;
     if (str_equal(d->d_name,"smtpgreeting")) continue;
     if (str_equal(d->d_name,"smtproutes")) continue;
     if (str_equal(d->d_name,"timeoutconnect")) continue;
index c4640b8b474fc8c682f15d15ba16fe8b107e1197..e53e263539f31e300dd20e184b1e2829f5463ef2 100644 (file)
@@ -128,18 +128,11 @@ is supplied,
 .B qmail-smtpd
 will reject
 any envelope recipient address with a domain not listed in
-.IR rcpthosts .
-
-Exception:
-If the environment variable
-.B RELAYCLIENT
-is set,
-.B qmail-smtpd
-will ignore
-.IR rcpthosts ,
-and will append the value of
-.B RELAYCLIENT
-to each incoming recipient address.
+.I rcpthosts
+unless the sending host is a designated relay client (see the
+description of the
+.I relayhosts
+file beow).
 
 .I rcpthosts
 may include wildcards:
@@ -152,6 +145,32 @@ may include wildcards:
 Envelope recipient addresses without @ signs are
 always allowed through.
 .TP 5
+.I relayhosts
+Allowed relay clients.  Each line is a host-suffix pair, separated by a
+colon.  If the client's hostname matches one of the hostnames in the
+file, that client is permitted to send mail to any host (i.e., to use us
+as a relay), and the corresponding suffix is appended to all recipient
+addresses generated by the client.
+
+.I relayhosts
+may include wildcards:
+
+.EX
+   heaven.af.mil:
+   .heaven.af.mil:
+   hell.irs.gov:.irs.virtdomain
+.EE
+
+For historical reasons, the
+.B RELAYCLIENT
+environment variable overrides this table.  If
+.B RELAYCLIENT
+is set, it has the same effect as there being a matching entry in the
+.I relayhosts
+file, using the value of
+.B RELAYCLIENT
+as the suffix.
+.TP 5
 .I smtpgreeting
 SMTP greeting message.
 Default:
index 1e28c88815bff2606131aaa115a3cf22beaa5994..6f453ce46fc150160ebdad46218913f9aa347c8c 100644 (file)
@@ -93,6 +93,9 @@ void dohelo(arg) char *arg; {
 
 int liphostok = 0;
 stralloc liphost = {0};
+int relayhostsok = 0;
+stralloc relayhosts = {0};
+struct constmap maprelayhosts;
 int bmfok = 0;
 stralloc bmf = {0};
 struct constmap mapbmf;
@@ -116,6 +119,16 @@ void setup()
   if (bmfok == -1) die_control();
   if (bmfok)
     if (!constmap_init(&mapbmf,bmf.s,bmf.len,0)) die_nomem();
+
+  switch (control_readfile(&relayhosts, "control/relayhosts", 0)) {
+    case -1:
+      die_control();
+    case 1:
+      relayhostsok = 1;
+      if (!constmap_init(&maprelayhosts, relayhosts.s, relayhosts.len, 1))
+       die_nomem();
+  }
+
  
   if (control_readint(&databytes,"control/databytes") == -1) die_control();
   x = env_get("DATABYTES");
@@ -131,6 +144,18 @@ void setup()
   if (!remotehost) remotehost = "unknown";
   remoteinfo = env_get("TCPREMOTEINFO");
   relayclient = env_get("RELAYCLIENT");
+  if (!relayclient && relayhostsok) {
+    int j;
+    int l = str_len(remotehost);
+    relayclient = constmap(&maprelayhosts, remotehost, l);
+    if (!relayclient) for (j = 0; j < l; ++j) {
+      if (remotehost[j] == '.' &&
+        (relayclient = constmap(&maprelayhosts,
+                                remotehost + j,
+                                l - j)) != 0)
+       break;
+    }
+  }
   dohelo(remotehost);
 }