]> git.ipfire.org Git - thirdparty/postfix.git/commitdiff
postfix-2.0.0-20030104
authorWietse Venema <wietse@porcupine.org>
Sat, 4 Jan 2003 05:00:00 +0000 (00:00 -0500)
committerViktor Dukhovni <viktor@dukhovni.org>
Tue, 5 Feb 2013 06:28:40 +0000 (06:28 +0000)
30 files changed:
postfix/HISTORY
postfix/RELEASE_NOTES
postfix/conf/main.cf
postfix/conf/sample-local.cf
postfix/conf/sample-misc.cf
postfix/conf/sample-smtpd.cf
postfix/html/faq.html
postfix/html/postconf.1.html
postfix/html/proxymap.8.html
postfix/html/trivial-rewrite.8.html
postfix/man/man8/proxymap.8
postfix/man/man8/trivial-rewrite.8
postfix/mantools/postlink
postfix/src/global/clnt_stream.c
postfix/src/global/dict_proxy.c
postfix/src/global/dict_proxy.h
postfix/src/global/mail_params.h
postfix/src/global/mail_version.h
postfix/src/global/resolve_clnt.c
postfix/src/global/rewrite_clnt.c
postfix/src/global/verify_clnt.c
postfix/src/global/virtual8_maps.c
postfix/src/global/virtual8_maps.h
postfix/src/local/local.c
postfix/src/proxymap/proxymap.c
postfix/src/trivial-rewrite/trivial-rewrite.c
postfix/src/util/dict.h
postfix/src/util/dict_open.c
postfix/src/util/vstream.c
postfix/src/virtual/virtual.c

index 9f25df299281b73c91180bbaad72fa5f077a95af..581117f68fbda61caf3dc9afd0a3a74c12073fab 100644 (file)
@@ -7630,11 +7630,8 @@ Apologies for any names omitted.
 
 20030102
 
-       Workaround: use different client instances when the same
-       map is opened with different flags. This silences warnings
-       from maps_append() when the same map is opened by
-       virtual_alias_maps and by virtual_mailbox_maps. File:
-       global/maps.c.
+       Cleanup: use different client instances when the same map
+       is opened with different flags. File: global/maps.c.
 
        Feature: proxymap server for Postfix table lookups. This
        helps to consolidate the number of open lookup tables (such
@@ -7649,6 +7646,25 @@ Apologies for any names omitted.
        after the limit is reached.  Based on a patch by Victor
        Duchovni, Morgan Stanley. File:  master/multi_server.c.
 
+20030103
+
+       Cleanup: client stream endpoints not only have an idle time
+       limit ($ipc_idle) before a connection is closed, they now
+       also have a time to live ($ipc_ttl) to prevent connections
+       from becoming too persistent. This allows multi-servers
+       such as trivial-rewrite or the proxymap server to refresh
+       more frequently on busy systems. File:  global/clnt_stream.c.
+
+20030104
+
+       Cleanup: avoid warnings about flag mismatches when the same
+       lookup table is listed under both virtual_alias_maps and
+       virtual_mailbox_maps. Files: global/virtual8.h, virtual/virtual.c.
+
+       Bugfix: an obscure memory leak that puzzled me for more
+       than a year until I found out how to reproduce it. File:
+       util/vstream.c.
+
 Open problems:
 
        Med: do not postpone rejected "MAIL FROM" size information,
index 24526a461b4f3cbbc59e9dac2a1eca522baa794d..68ae6f7a009b94dc5dad97b1cd93ecd916ac3919 100644 (file)
@@ -22,6 +22,37 @@ snapshot release).  Patches change the patchlevel and the release
 date. Snapshots change only the release date, unless they include
 the same bugfixes as a patch release.
 
+Incompatible changes with Postfix snapshot 2.0.0-20030104
+=========================================================
+
+This release adds the new proxymap service (table lookup via a
+proxy process) to the the master.cf file. If you get warnings about
+problems connecting to the proxymap service, then you did not
+properly upgrade Postfix.
+
+Major changes with Postfix snapshot 2.0.0-20030104
+==================================================
+
+This release introduces the proxymap service for Postfix lookup
+table access. This can be used to overcome chroot restrictions in
+the Postfix SMTP server (specify proxy:unix:passwd.byname for
+password file lookup through the proxymap server) and can be used
+to consolidate the number of open tables by sharing one open table
+among multiple processes (specify proxy:mysql:/file/name to avoid
+"too many connections" conditions). The proxy_read_maps parameter
+specifies what maps are approved for access via the proxy service
+(only map references starting with "proxy:" are considered approved).
+
+Multi-server daemons (servers that accept simultaneous connections
+from multiple clients) will now stop accepting new connections
+after serving $max_use clients. This allows multi-server daemons
+to automatically restart even on busy mail systems.
+
+Clients of multi-server daemons such as trivial-rewrite and the
+new proxymap service now automatically disconnect after $ipc_ttl
+seconds of activity (default: 1000s). This allows multi-server
+daemons to automatically restart even on busy mail mail systems.
+
 Incompatible changes with Postfix snapshot 1.1.11-trace-20021119
 ================================================================
 
index c5ebc9987e1ca256f6fdd3e145036605a40f66f3..f088bd1c985353af9e091d31bb0ff106ce0b1498 100644 (file)
@@ -175,18 +175,20 @@ mail_owner = postfix
 #   For example, you define $mydestination domain recipients in    
 #   the $virtual_mailbox_maps files.
 #
-# - You redefined the local delivery agent in master.cf.
+# - You redefine the local delivery agent in master.cf.
 #
-# - You redefined the "local_transport" setting in main.cf.
+# - You redefine the "local_transport" setting in main.cf.
 #
 # - You use the "luser_relay", "mailbox_transport", or "fallback_transport"
 #   feature of the Postfix local delivery agent (see sample-local.cf).
 #
 # Beware: if the Postfix SMTP server runs chrooted, you probably have
-# to copy the passwd (not shadow) database into the jail, and perhaps
-# other files. This is system dependent.
+# to access the passwd file via the proxymap service, in order to
+# overcome chroot restrictions. The alternative, having a copy of
+# the system passwd file in the chroot jail is just not practical.
 # 
 #local_recipient_maps = unix:passwd.byname $alias_maps
+#local_recipient_maps = proxy:passwd.byname $alias_maps
 #local_recipient_maps =
 
 # The unknown_local_recipient_reject_code specifies the SMTP server
index c901c0b2425f9643ca9289a748ac11fddb565452..e15bff23218ef316625ddc8e55dec1f05cf72b90 100644 (file)
 # precedence, from highest to lowest priority: mailbox_transport,
 # mailbox_command_maps, mailbox_command, home_mailbox.
 
+#
+# MISCELLANEOUS PARAMETERS
+#
+
 # The biff parameter specifies whether or not to contact the biff
 # server.  This server sends "new mail" notifications to users who
 # have requested new mail notification with "biff y".   
index 18792e312f22b826d68418e539eed4ff91baeb6f..2c83b8a348ae7084e0cee97f41656f14a3d4383b 100644 (file)
@@ -236,7 +236,7 @@ max_use = 100
 # a name matches a lookup key.  Continue long lines by starting the
 # next line with whitespace.
 #
-# See sample-local.cf for a description of the local_recipient_maps
+# See sample-smtpd.cf for a description of the local_recipient_maps
 # and unknown_local_recipient_reject_code parameters. By default,
 # the SMTP server rejects mail for recipients not listed with the
 # local_recipient_maps parameter.
index 4fd7c08ccd826890a656e1b8aa03a2547bef1ef8..ac9b17bef3d592534665e819e62430d66b69d29e 100644 (file)
@@ -4,6 +4,65 @@
 # This file contains example settings of Postfix configuration parameters
 # that control the SMTP server program.
 
+# REJECTING MAIL FOR UNKNOWN LOCAL USERS
+#
+# The local_recipient_maps parameter specifies optional lookup tables
+# with all names or addresses of users that are local with respect
+# to $mydestination and $inet_interfaces.
+#
+# If this parameter is defined, then the SMTP server will reject
+# mail for unknown local users. This parameter is defined by default.
+#
+# To turn off local recipient checking in the SMTP server, specify
+# local_recipient_maps = (i.e. empty).
+#
+# The default setting assumes that you use the default Postfix local
+# delivery agent for local delivery. You need to update the
+# local_recipient_maps setting if:
+#
+# - You define $mydestination domain recipients in files other than
+#   /etc/passwd, /etc/aliases, or the $virtual_alias_maps files.
+#   For example, you define $mydestination domain recipients in    
+#   the $virtual_mailbox_maps files.
+#
+# - You redefine the local delivery agent in master.cf.
+#
+# - You redefine the "local_transport" setting in main.cf.
+#
+# - You use the "luser_relay", "mailbox_transport", or "fallback_transport"
+#   feature of the Postfix local delivery agent (see sample-local.cf).
+#
+# Beware: if the Postfix SMTP server runs chrooted, you probably have
+# to access the passwd file via the proxymap service, in order to
+# overcome chroot restrictions. The alternative, having a copy of
+# the system passwd file in the chroot jail is just not practical.
+# 
+#local_recipient_maps =
+#local_recipient_maps = unix:passwd.byname $alias_maps
+local_recipient_maps = proxy:passwd.byname $alias_maps
+
+# The unknown_local_recipient_reject_code specifies the SMTP server
+# response code when a recipient domain matches $mydestination or
+# $inet_interfaces, while $local_recipient_maps is non-empty and the
+# recipient address or address local-part is not found.
+#
+# The default setting is 550 (reject mail) but it is safer to start
+# with 450 (try again later) until you are certain that your
+# local_recipient_maps settings are OK.
+#
+#unknown_local_recipient_reject_code = 450
+unknown_local_recipient_reject_code = 550
+
+# REJECTING UNKNOWN RELAY USERS
+#
+# The relay_recipient_maps parameter specifies optional lookup tables
+# with all addresses in the domains that match $relay_domains.
+#
+# If this parameter is defined, then the SMTP server will reject
+# mail for unknown relay users. This feature is off by default.
+# 
+#relay_recipient_maps = hash:/etc/postfix/relay_recipients
+
 #
 # SENDER ANTI-SPOOFING
 #
index 587d0e2838cf9b76ed2514ffef4101a2d6ce63c0..31ef4b176b8aa15816a62788e44cc7c165e7694a 100644 (file)
@@ -674,7 +674,7 @@ to send mail only to <i>user@domain.com</i>.
 Specify what recipients exist (so that your queue does not fill up
 with undeliverable mail from spammers).
 
-<p.
+<p>
 
 Specify <tt>local_recipient_maps =</tt> if maintaining recipient
 information is not practical.
@@ -2090,7 +2090,7 @@ you use the default Postfix local delivery agent:
 
 <pre>
     /etc/postfix/main.cf:
-        local_recipient_maps = $alias_maps, unix:passwd.byname
+        local_recipient_maps = $alias_maps, proxy:unix:passwd.byname
 </pre>
 
 <p>
@@ -2107,10 +2107,12 @@ To stop Postfix from rejecting local mail incorrectly:
 
 <ul>
 
-<li> If you run the Postfix SMTP server chrooted, it may be necessary
-to place a copy of the passwd file inside the chroot jail (typically:
-in <b>/var/spool/postfix/etc</b>).  This is system dependent. The
-only way to find out is to try.
+<li> If you run the Postfix SMTP server chrooted, you need to access
+the system password database through the Postfix <a href="proxymap.8.html">
+proxymap</a> service, as shown in the above example. The alternative
+is simply not practical:  placing a copy of the passwd file inside
+the chroot jail (typically:  in <b>/var/spool/postfix/etc</b>)
+together with a list of system dependent files.
 
 <p>
 
@@ -2313,21 +2315,30 @@ database" mean?</h3></a>
 This message is logged when, for example, the Postfix SMTP server
 is unable to access the UNIX password database.
 
+<p>
+
 <ul>
 
 <li> If you're running the Postfix SMTP server chrooted (see
-<b>master.cf</b>) then you may have to copy the password file and
-perhaps a bunch of other files into the Postfix queue directory; a
-typical destination would be <b>/var/spool/postfix/etc</b>. See also
-the chroot setup scripts in the <b>examples</b> directory of the
-Postfix source code distribution.
+<b>master.cf</b>) then you need to access the system password
+database through the Postfix <a href="proxymap.8.html">proxymap</a>
+service. The alternative is not practical: copying the password
+file and perhaps a bunch of other system dependent files into the
+Postfix queue directory.
+
+<p>
+
+<pre>
+    /etc/postfix/main.cf:
+       local_recipient_maps = proxy:unix:passwd.byname $alias_maps ...
+</pre>
 
 <p>
 
-<li> Be sure that you have world execute permissions on directories
-and world read permission on the passwd file and any auxiliary
-files that may be needed (such as <b>/etc/nsswitch.conf</b> and
-<b>libnss*.so*</b> files referenced by <b>/etc/nsswitch.conf</b>).
+<li> Chrooted or not, be sure that you have world execute permissions
+on directories and world read permission on the passwd file and
+any auxiliary files that may be needed (such as <b>/etc/nsswitch.conf</b>
+and <b>libnss*.so*</b> files referenced by <b>/etc/nsswitch.conf</b>).
 
 </ul>
 
index b13c0357d33190419d1401682027ba40b5f8d350..4289928bfe276e1fd2eda0b866132fb7d312342d 100644 (file)
@@ -91,7 +91,7 @@ POSTCONF(1)                                           POSTCONF(1)
 
               <b>proxy</b> (read-only)
                      A lookup table that is implemented  via  the
-                     Postfix  <a href="verify.8.html"><b>proxymap</b>(8)</a> service. The table name
+                     Postfix  <a href="proxymap.8.html"><b>proxymap</b>(8)</a> service. The table name
                      syntax is <i>type</i><b>:</b><i>name</i>.
 
               <b>regexp</b> (read-only)
index bc96ab220d2e7b70fbbc87b7c316127b983cd788..e1d0cf4b743506b5b3831cb0a563ab55e196d528 100644 (file)
@@ -15,34 +15,39 @@ PROXYMAP(8)                                           PROXYMAP(8)
        <b>o</b>      To  overcome  chroot  restrictions.  For example, a
               chrooted SMTP server needs  access  to  the  system
               passwd  file  in order to reject mail for non-exis-
-              tent local addresses.  The solution is to specify:
+              tent local addresses, but it is  not  practical  to
+              maintain  a  copy  of the passwd file in the chroot
+              jail.  The solution:
 
               local_recipient_maps =
                   proxy:unix:passwd.byname $alias_maps
 
        <b>o</b>      To consolidate the number of open lookup tables  by
               sharing  one  open  table among multiple processes.
-              For example, to avoid problems  due  to  "too  many
-              connections" to, e.g., mysql servers, specify:
+              For example, making mysql  connections  from  every
+              Postfix daemon process results in "too many connec-
+              tions" errors. The solution:
 
               virtual_alias_maps =
                   proxy:mysql:/etc/postfix/virtual.cf
 
-<b>PROXYMAP</b> <b>SERVICES</b>
+              The total number of connections is limited  by  the
+              number of proxymap server server processes.
+
        The proxymap server implements the following requests:
 
        <b>PROXY</b><i>_</i><b>REQ</b><i>_</i><b>OPEN</b> <i>maptype:mapname</i> <i>flags</i>
               Open  the table with type <i>maptype</i> and name <i>mapname</i>,
               as controlled by <i>flags</i>.  The reply is  the  request
-              completion  status  code and the map type dependent
-              flags.
+              completion  status  code  (below)  and the map type
+              dependent flags.
 
        <b>PROXY</b><i>_</i><b>REQ</b><i>_</i><b>LOOKUP</b> <i>maptype:mapname</i> <i>flags</i> <i>key</i>
               Look up the data stored under  the  requested  key.
-              The reply is the request completion status code and
-              the lookup result value.  The  <i>maptype:mapname</i>  and
-              <i>flags</i>  are  the  same  as  with  the <b>PROXY</b><i>_</i><b>REQ</b><i>_</i><b>OPEN</b>
-              request.
+              The  reply  is  the  request completion status code
+              (below) and the  lookup  result  value.   The  <i>map-</i>
+              <i>type:mapname</i>  and  <i>flags</i>  are  the same as with the
+              <b>PROXY</b><i>_</i><b>REQ</b><i>_</i><b>OPEN</b> request.
 
        There is no close command. This does not seem to be useful
        because  tables  are  meant to be shared among client pro-
@@ -51,52 +56,63 @@ PROXYMAP(8)                                           PROXYMAP(8)
        The request completion status code is one of:
 
        <b>PROXY</b><i>_</i><b>STAT</b><i>_</i><b>OK</b>
-              The requested table or lookup key was found.
+              The specified table was opened,  or  the  requested
+              entry was found.
 
-       <b>PROXY</b><i>_</i><b>STAT</b><i>_</i><b>FAIL</b>
-              The requested table or lookup key does not exist.
+       <b>PROXY</b><i>_</i><b>STAT</b><i>_</i><b>NOKEY</b>
+              The requested table entry was not found.
 
        <b>PROXY</b><i>_</i><b>STAT</b><i>_</i><b>BAD</b>
-              The request was  rejected  (bad  request  parameter
+              The  request  was  rejected  (bad request parameter
               value).
 
        <b>PROXY</b><i>_</i><b>STAT</b><i>_</i><b>RETRY</b>
-              The request was not completed.
+              The lookup request could not be completed.
+
+       <b>PROXY</b><i>_</i><b>STAT</b><i>_</i><b>DENY</b>
+              The specified table was not approved for access via
+              the proxymap service.
 
-<b>MASTER</b> <b>INTERFACE</b>
+<b>SERVER</b> <b>PROCESS</b> <b>MANAGEMENT</b>
        The proxymap servers run under control by the Postfix mas-
        ter server.  Each server can handle multiple  simultaneous
        connections.   When  all  servers  are busy while a client
        connects, the master creates a new  proxymap  server  pro-
        cess,  provided  that the proxymap server process limit is
-       not exceeded.  Each proxymap server terminates after serv-
-       ing  <b>$max</b><i>_</i><b>use</b>  clients  or after <b>$max</b><i>_</i><b>idle</b> seconds of idle
-       time.
+       not exceeded.  Each proxymap server  stops  accepting  new
+       connections  after  serving <b>$max</b><i>_</i><b>use</b> clients or terminates
+       after <b>$max</b><i>_</i><b>idle</b> seconds of idle time.
 
 <b>SECURITY</b>
-       The proxymap server is not  security-sensitive.  It  opens
-       only tables that are approved via the <b>proxymap</b><i>_</i><b>filter</b> con-
-       figuration parameter, does not talk to users, and can  run
-       at fixed low privilege, chrooted or not.
+       The proxymap server opens only tables  that  are  approved
+       via  the <b>proxy</b><i>_</i><b>read</b><i>_</i><b>maps</b> configuration parameter, does not
+       talk to  users,  and  can  run  at  fixed  low  privilege,
+       chrooted or not.
+
+       The  proxymap  server is not a trusted daemon process, and
+       must not be used to look up sensitive information such  as
+       user  or group IDs, mailbox file/directory names or exter-
+       nal commands.
 
 <b>DIAGNOSTICS</b>
        Problems and transactions are logged to <b>syslogd</b>(8).
 
 <b>BUGS</b>
-       The  proxymap server provides service to multiple clients,
-       and must therefore not be used for tables that have  high-
+       The proxymap server provides service to multiple  clients,
+       and  must therefore not be used for tables that have high-
        latency lookups.
 
 <b>CONFIGURATION</b> <b>PARAMETERS</b>
-       The  following  main.cf parameters are especially relevant
-       to this program. Use the <b>postfix</b> <b>reload</b>  command  after  a
+       The following main.cf parameters are  especially  relevant
+       to  this  program.  Use the <b>postfix</b> <b>reload</b> command after a
        configuration change.
 
-       <b>proxymap</b><i>_</i><b>filter</b>
-              A  list  of  zero or more parameter values that may
-              contain Postfix lookup table references. Only table
-              references  that begin with <b>proxy:</b> are approved for
-              access via the proxymap server.
+       <b>proxy</b><i>_</i><b>read</b><i>_</i><b>maps</b>
+              A list of zero or more parameter  values  that  may
+              contain  references  to Postfix lookup tables. Only
+              table  references  that  begin  with   <b>proxy:</b>   are
+              approved  for  read-only  access  via  the proxymap
+              server.
 
 <b>SEE</b> <b>ALSO</b>
        dict_proxy(3) proxy map client
index 97ce29da96e0cc3c688169c3f25a369c05e86bc5..9705a6732653b48ebc28431d3f7fb7431e430fc9 100644 (file)
@@ -37,14 +37,6 @@ TRIVIAL-REWRITE(8)                             TRIVIAL-REWRITE(8)
                      The  envelope  recipient  address  that   is
                      passed on to <i>nexthop</i>.
 
-       <b>trivial-rewrite</b>  servers  run under control by the Postfix
-       master server. Each server can handle multiple  simultane-
-       ous connections.  When all servers are busy while a client
-       connects, a new server process is created,  provided  that
-       the  trivial-rewrite server process limit is not exceeded.
-       Each server terminates after serving <b>$max</b><i>_</i><b>use</b>  clients  or
-       after <b>$max</b><i>_</i><b>idle</b> seconds of idle time.
-
 <b>DEFAULT</b> <b>DELIVERY</b> <b>METHODS</b>
        By  default,  Postfix  uses  one of the following delivery
        methods.  This may be overruled with the  optional  <a href="transport.5.html">trans-</a>
@@ -83,14 +75,24 @@ TRIVIAL-REWRITE(8)                             TRIVIAL-REWRITE(8)
               <b>$relayhost</b>.   The  default nexthop is the recipient
               domain.
 
+<b>SERVER</b> <b>PROCESS</b> <b>MANAGEMENT</b>
+       The trivial-rewrite servers run under control by the Post-
+       fix master server.  Each server can handle multiple simul-
+       taneous connections.  When all servers are  busy  while  a
+       client  connects, the master creates a new server process,
+       provided that the trivial-rewrite server process limit  is
+       not exceeded.  Each trivial-rewrite server stops accepting
+       new connections after serving <b>$max</b><i>_</i><b>use</b> clients  or  termi-
+       nates after <b>$max</b><i>_</i><b>idle</b> seconds of idle time.
+
 <b>STANDARDS</b>
-       None. The command  does  not  interact  with  the  outside
+       None.  The  command  does  not  interact  with the outside
        world.
 
 <b>SECURITY</b>
-       The  <b>trivial-rewrite</b> daemon is not security sensitive.  By
-       default, this daemon does not  talk  to  remote  or  local
-       users.   It can run at a fixed low privilege in a chrooted
+       The <b>trivial-rewrite</b> daemon is not security sensitive.   By
+       default,  this  daemon  does  not  talk to remote or local
+       users.  It can run at a fixed low privilege in a  chrooted
        environment.
 
 <b>DIAGNOSTICS</b>
@@ -98,21 +100,21 @@ TRIVIAL-REWRITE(8)                             TRIVIAL-REWRITE(8)
 
 <b>BUGS</b>
 <b>CONFIGURATION</b> <b>PARAMETERS</b>
-       The following <b>main.cf</b> parameters are  especially  relevant
-       to  this  program. See the Postfix <b>main.cf</b> file for syntax
-       details and for default values.  Use  the  <b>postfix</b>  <b>reload</b>
+       The  following  <b>main.cf</b> parameters are especially relevant
+       to this program. See the Postfix <b>main.cf</b> file  for  syntax
+       details  and  for  default  values. Use the <b>postfix</b> <b>reload</b>
        command after a configuration change.
 
 <b>Miscellaneous</b>
        <b>empty</b><i>_</i><b>address</b><i>_</i><b>recipient</b>
-              The  recipient  that  is  substituted  for the null
+              The recipient that  is  substituted  for  the  null
               address.
 
        <b>inet</b><i>_</i><b>interfaces</b>
-              The  network  interfaces  that  this  mail   system
-              receives  mail  on.   This  information  is used to
-              determine if <i>user</i>@[<i>net.work.addr.ess</i>] is  local  or
-              remote.   Mail  for  local  users  is  given to the
+              The   network  interfaces  that  this  mail  system
+              receives mail on.   This  information  is  used  to
+              determine  if  <i>user</i>@[<i>net.work.addr.ess</i>] is local or
+              remote.  Mail for  local  users  is  given  to  the
               <b>$local</b><i>_</i><b>transport</b>.
 
        <b>mydestination</b>
@@ -121,7 +123,7 @@ TRIVIAL-REWRITE(8)                             TRIVIAL-REWRITE(8)
 
        <b>virtual</b><i>_</i><b>alias</b><i>_</i><b>domains</b>
               List of simulated virtual domains (domains with all
-              recipients aliased to some other  local  or  remote
+              recipients  aliased  to  some other local or remote
               domain).
 
        <b>virtual</b><i>_</i><b>mailbox</b><i>_</i><b>domains</b>
@@ -134,10 +136,10 @@ TRIVIAL-REWRITE(8)                             TRIVIAL-REWRITE(8)
 
        <b>resolve</b><i>_</i><b>unquoted</b><i>_</i><b>address</b>
               When resolving an address, do not quote the address
-              localpart as per <a href="http://www.faqs.org/rfcs/rfc822.html">RFC 822</a>, so that additional  <b>@</b>,  <b>%</b>
-              or  <b>!</b>   characters  remain visible. This is techni-
+              localpart  as  per <a href="http://www.faqs.org/rfcs/rfc822.html">RFC 822</a>, so that additional <b>@</b>, <b>%</b>
+              or <b>!</b>  characters remain visible.  This  is  techni-
               cally  incorrect,  but  allows  us  to  stop  relay
-              attacks  when forwarding mail to a Sendmail primary
+              attacks when forwarding mail to a Sendmail  primary
               MX host.
 
        <b>relocated</b><i>_</i><b>maps</b>
@@ -163,50 +165,50 @@ TRIVIAL-REWRITE(8)                             TRIVIAL-REWRITE(8)
 
 <b>Routing</b>
        <b>local</b><i>_</i><b>transport</b>
-              Where to deliver mail for destinations  that  match
-              <b>$mydestination</b>  or  <b>$inet</b><i>_</i><b>interfaces</b>.   The default
+              Where  to  deliver mail for destinations that match
+              <b>$mydestination</b> or  <b>$inet</b><i>_</i><b>interfaces</b>.   The  default
               transport is <b>local:$myhostname</b>.
 
-              Syntax is <i>transport</i>:<i>nexthop</i>; see  <a href="transport.5.html"><b>transport</b>(5)</a>  for
+              Syntax  is  <i>transport</i>:<i>nexthop</i>; see <a href="transport.5.html"><b>transport</b>(5)</a> for
               details. The :<i>nexthop</i> part is optional.
 
        <b>virtual</b><i>_</i><b>transport</b>
-              Where  to  deliver  mail for non-local domains that
+              Where to deliver mail for  non-local  domains  that
               match <b>$virtual</b><i>_</i><b>mailbox</b><i>_</i><b>domains</b>.  The default trans-
               port is <b>virtual</b>.
 
-              Syntax  is  <i>transport</i>:<i>nexthop</i>; see <a href="transport.5.html"><b>transport</b>(5)</a> for
+              Syntax is <i>transport</i>:<i>nexthop</i>; see  <a href="transport.5.html"><b>transport</b>(5)</a>  for
               details. The :<i>nexthop</i> part is optional.
 
        <b>relay</b><i>_</i><b>transport</b>
-              Where to deliver mail for  non-local  domains  that
-              match  <b>$relay</b><i>_</i><b>domains</b>.   The  default  transport is
+              Where  to  deliver  mail for non-local domains that
+              match <b>$relay</b><i>_</i><b>domains</b>.   The  default  transport  is
               <b>relay</b> (which normally is a clone of the <b>smtp</b> trans-
               port).
 
-              Syntax  is  <i>transport</i>:<i>nexthop</i>; see <a href="transport.5.html"><b>transport</b>(5)</a> for
+              Syntax is <i>transport</i>:<i>nexthop</i>; see  <a href="transport.5.html"><b>transport</b>(5)</a>  for
               details. The :<i>nexthop</i> part is optional.
 
        <b>default</b><i>_</i><b>transport</b>
-              Where to deliver all  other  non-local  mail.   The
+              Where  to  deliver  all  other non-local mail.  The
               default transport is <b>smtp</b>.
 
-              Syntax  is  <i>transport</i>:<i>nexthop</i>; see <a href="transport.5.html"><b>transport</b>(5)</a> for
+              Syntax is <i>transport</i>:<i>nexthop</i>; see  <a href="transport.5.html"><b>transport</b>(5)</a>  for
               details. The :<i>nexthop</i> part is optional.
 
        <b>parent</b><i>_</i><b>domain</b><i>_</i><b>matches</b><i>_</i><b>subdomains</b>
-              List of Postfix features that use  <i>domain.tld</i>  pat-
-              terns   to  match  <i>sub.domain.tld</i>  (as  opposed  to
+              List  of  Postfix features that use <i>domain.tld</i> pat-
+              terns  to  match  <i>sub.domain.tld</i>  (as  opposed   to
               requiring <i>.domain.tld</i> patterns).
 
        <b>relayhost</b>
-              The default host to send non-local mail to when  no
-              host   is   specified   with   <b>$relay</b><i>_</i><b>transport</b>  or
-              <b>$default</b><i>_</i><b>transport</b>, and when the recipient  address
+              The  default host to send non-local mail to when no
+              host  is   specified   with   <b>$relay</b><i>_</i><b>transport</b>   or
+              <b>$default</b><i>_</i><b>transport</b>,  and when the recipient address
               does not match the optional the <a href="transport.5.html"><b>transport</b>(5)</a> table.
 
        <b>transport</b><i>_</i><b>maps</b>
-              List of tables with <i>recipient</i> or <i>domain</i> to  (<i>trans-</i>
+              List  of tables with <i>recipient</i> or <i>domain</i> to (<i>trans-</i>
               <i>port,</i> <i>nexthop</i>) mappings.
 
 <b>SEE</b> <b>ALSO</b>
@@ -216,7 +218,7 @@ TRIVIAL-REWRITE(8)                             TRIVIAL-REWRITE(8)
        <a href="relocated.5.html">relocated(5)</a> format of the "user has moved" table
 
 <b>LICENSE</b>
-       The  Secure  Mailer  license must be distributed with this
+       The Secure Mailer license must be  distributed  with  this
        software.
 
 <b>AUTHOR(S)</b>
index 533ef958d4a2e90a717d64f4a88e137c44ab1000..876563fdbdf86f04c9dac5e6bd8c38aa51f4fc6d 100644 (file)
@@ -18,35 +18,35 @@ of the service is:
 .IP \(bu
 To overcome chroot restrictions. For example, a chrooted SMTP
 server needs access to the system passwd file in order to
-reject mail for non-existent local addresses.
-The solution is to specify:
+reject mail for non-existent local addresses, but it is not
+practical to maintain a copy of the passwd file in the chroot
+jail.  The solution:
 .sp
 local_recipient_maps =
 .ti +4
 proxy:unix:passwd.byname $alias_maps
 .IP \(bu
 To consolidate the number of open lookup tables by sharing
-one open table among multiple processes. For example, to avoid
-problems due to "too many connections" to, e.g., mysql servers,
-specify:
+one open table among multiple processes. For example, making
+mysql connections from every Postfix daemon process results
+in "too many connections" errors. The solution:
 .sp
 virtual_alias_maps =
 .ti +4
 proxy:mysql:/etc/postfix/virtual.cf
-.SH PROXYMAP SERVICES
-.na
-.nf
-.ad
-.fi
+.sp
+The total number of connections is limited by the number of
+proxymap server server processes.
+.PP
 The proxymap server implements the following requests:
 .IP "\fBPROXY_REQ_OPEN\fI maptype:mapname flags\fR"
 Open the table with type \fImaptype\fR and name \fImapname\fR,
 as controlled by \fIflags\fR.
-The reply is the request completion status code and the
+The reply is the request completion status code (below) and the
 map type dependent flags.
 .IP "\fBPROXY_REQ_LOOKUP\fI maptype:mapname flags key\fR"
 Look up the data stored under the requested key.
-The reply is the request completion status code and
+The reply is the request completion status code (below) and
 the lookup result value.
 The \fImaptype:mapname\fR and \fIflags\fR are the same
 as with the \fBPROXY_REQ_OPEN\fR request.
@@ -56,14 +56,17 @@ because tables are meant to be shared among client processes.
 
 The request completion status code is one of:
 .IP \fBPROXY_STAT_OK\fR
-The requested table or lookup key was found.
-.IP \fBPROXY_STAT_FAIL\fR
-The requested table or lookup key does not exist.
+The specified table was opened, or the requested entry was found.
+.IP \fBPROXY_STAT_NOKEY\fR
+The requested table entry was not found.
 .IP \fBPROXY_STAT_BAD\fR
 The request was rejected (bad request parameter value).
 .IP \fBPROXY_STAT_RETRY\fR
-The request was not completed.
-.SH MASTER INTERFACE
+The lookup request could not be completed.
+.IP \fBPROXY_STAT_DENY\fR
+The specified table was not approved for access via the
+proxymap service.
+.SH SERVER PROCESS MANAGEMENT
 .na
 .nf
 .ad
@@ -73,17 +76,21 @@ server.  Each server can handle multiple simultaneous connections.
 When all servers are busy while a client connects, the master
 creates a new proxymap server process, provided that the proxymap
 server process limit is not exceeded.
-Each proxymap server terminates after serving \fB$max_use\fR clients
-or after \fB$max_idle\fR seconds of idle time.
+Each proxymap server stops accepting new connections after serving
+\fB$max_use\fR clients or terminates after \fB$max_idle\fR seconds
+of idle time.
 .SH SECURITY
 .na
 .nf
 .ad
 .fi
-The proxymap server is not security-sensitive. It opens only
-tables that are approved via the \fBproxymap_filter\fR
-configuration parameter, does not talk to users, and
-can run at fixed low privilege, chrooted or not.
+The proxymap server opens only tables that are approved via the
+\fBproxy_read_maps\fR configuration parameter, does not talk to
+users, and can run at fixed low privilege, chrooted or not.
+
+The proxymap server is not a trusted daemon process, and must
+not be used to look up sensitive information such as user or
+group IDs, mailbox file/directory names or external commands.
 .SH DIAGNOSTICS
 .ad
 .fi
@@ -102,11 +109,11 @@ lookups.
 The following main.cf parameters are especially relevant
 to this program. Use the \fBpostfix reload\fR command
 after a configuration change.
-.IP \fBproxymap_filter\fR
+.IP \fBproxy_read_maps\fR
 A list of zero or more parameter values that may contain
-Postfix lookup table references. Only table references that
-begin with \fBproxy:\fR are approved for access via the
-proxymap server.
+references to Postfix lookup tables. Only table references
+that begin with \fBproxy:\fR are approved for read-only
+access via the proxymap server.
 .SH SEE ALSO
 .na
 .nf
index bd56ad96fe7be8349b0a2b8e88db33f889531579..807bcb85e12cfdec8b2d602daf411776eb5650a4 100644 (file)
@@ -32,14 +32,6 @@ The host to send to and optional delivery method information.
 .IP \fIrecipient\fR
 The envelope recipient address that is passed on to \fInexthop\fR.
 .RE
-.PP
-\fBtrivial-rewrite\fR servers run under control by the Postfix master
-server. Each server can handle multiple simultaneous connections.
-When all servers are busy while a client connects, a new server
-process is created, provided that the trivial-rewrite server
-process limit is not exceeded.
-Each server terminates after serving \fB$max_use\fR clients
-or after \fB$max_idle\fR seconds of idle time.
 .SH DEFAULT DELIVERY METHODS
 .na
 .nf
@@ -73,6 +65,19 @@ The transport and optional nexthop are specified with
 This overrides the optional nexthop information that is specified
 with \fB$relayhost\fR.
 The default nexthop is the recipient domain.
+.SH SERVER PROCESS MANAGEMENT
+.na
+.nf
+.ad
+.fi
+The trivial-rewrite servers run under control by the Postfix master
+server.  Each server can handle multiple simultaneous connections.
+When all servers are busy while a client connects, the master
+creates a new server process, provided that the trivial-rewrite
+server process limit is not exceeded.
+Each trivial-rewrite server stops accepting new connections after
+serving \fB$max_use\fR clients or terminates after \fB$max_idle\fR
+seconds of idle time.
 .SH STANDARDS
 .na
 .nf
index be5d77bb43da83ccb8d7cab2b0b0f0620d9cfcaa..1f6d26ebd6825f9212236a505ba5a9f7ae49b14b 100755 (executable)
@@ -44,7 +44,7 @@ exec sed '
        s/[<bB>]*canonical[</bB>]*(5)/<a href="canonical.5.html">&<\/a>/
        s/[<bB>]*etrn[</bB>]*(5)/<a href="etrn.5.html">&<\/a>/
        s/[<bB>]*pcre[</bBiI>]*_[</iIbB>]*table[</bB>]*(5)/<a href="pcre_table.5.html">&<\/a>/
-       s/[<bB>]*proxymap[</bB>]*(8)/<a href="verify.8.html">&<\/a>/
+       s/[<bB>]*proxymap[</bB>]*(8)/<a href="proxymap.8.html">&<\/a>/
        s/[<bB>]*reg[-</bB>]*\n*[ <bB>]*exp[</bBiI>]*_[</iIbB>]*table[</bB>]*(5)/<a href="regexp_table.5.html">&<\/a>/
        s/[<bB>]*relocated[</bB>]*(5)/<a href="relocated.5.html">&<\/a>/
        s/[<bB>]*trans[-</bB>]*\n*[ <bB>]*port[</bB>]*(5)/<a href="transport.5.html">&<\/a>/
index 7c182372a81a4c98c8b419387cd12e9556fce6ee..8a736939e5dff2562157739af7eb1d6d35cb2168 100644 (file)
@@ -48,7 +48,7 @@
 /* .IP timeout
 /*     Idle time after which the client disconnects.
 /* .IP ttl
-/*     Time to live after which the client disconnects.
+/*     Upper bound on the time that a connection is allowed to persist.
 /* DIAGNOSTICS
 /*     Warnings: communication failure. Fatal error: mail system is down,
 /*     out of memory.
@@ -121,10 +121,16 @@ static void clnt_stream_ttl_event(int event, char *context)
 {
 
     /*
-     * XXX This function is needed only because the event_request_timer()
-     * function cannot distinguish requests with the same callback routine.
-     * The fix is obvious: specify a request ID along with the callback
-     * routine, but there is too much code that would have to be changed.
+     * XXX This function is needed only because event_request_timer() cannot
+     * distinguish between requests that specify the same call-back routine
+     * and call-back context. The fix is obvious: specify a request ID along
+     * with the call-back routine, but there is too much code that would have
+     * to be changed.
+     * 
+     * XXX Should we be concerned that an overly agressive optimizer will
+     * eliminate this function and replace calls to clnt_stream_ttl_event()
+     * by direct calls to clnt_stream_event()? It should not, because there
+     * exists code that takes the address of both functions.
      */
     clnt_stream_event(event, context);
 }
index 626eb9a3e1e7c1c0fc23eadda3d015e5154f344c..6cbe8ee59c0f8f3b88eca7988596db9d5474e9cf 100644 (file)
@@ -17,7 +17,8 @@
 /*     The \fIopen_flags\fR argument must specify O_RDONLY.
 /*
 /*     The connection to the Postfix proxymap server is automatically
-/*     closed after $ipc_idle seconds of idle time.
+/*     closed after $ipc_idle seconds of idle time, or after $ipc_ttl
+/*     seconds of activity.
 /* SECURITY
 /*      The proxy map server is not meant to be a trusted process. Proxy
 /*     maps must not be used to look up security sensitive information
@@ -27,7 +28,7 @@
 /*     clnt_stream(3) client endpoint connection management
 /* DIAGNOSTICS
 /*     Fatal errors: out of memory, unimplemented operation,
-/*     bad request parameter.
+/*     bad request parameter, map not approved for proxy access.
 /* LICENSE
 /* .ad
 /* .fi
@@ -78,8 +79,7 @@ typedef struct {
 #define VSTREQ(v,s)    (strcmp(STR(v),s) == 0)
 
  /*
-  * All proxied maps within the same process share the same query/reply
-  * socket.
+  * All proxied maps within a process share the same query/reply socket.
   */
 static CLNT_STREAM *proxy_stream;
 
@@ -115,25 +115,31 @@ static const char *dict_proxy_lookup(DICT *dict, const char *key)
                         ATTR_TYPE_STR, MAIL_ATTR_VALUE, dict_proxy->result,
                         ATTR_TYPE_END) != 2) {
            if (msg_verbose || (errno != EPIPE && errno != ENOENT))
-               msg_warn("%s: service %s: %m", VSTREAM_PATH(stream), myname);
+               msg_warn("%s: service %s: %m", myname, VSTREAM_PATH(stream));
        } else {
            if (msg_verbose)
                msg_info("%s: table=%s flags=0%o key=%s -> status=%d result=%s",
                         myname, dict->name, dict_proxy->in_flags, key,
                         status, STR(dict_proxy->result));
-           if (status == PROXY_STAT_OK) {
+           switch (status) {
+           case PROXY_STAT_BAD:
+               msg_fatal("%s lookup failed for table \"%s\" key \"%s\": "
+                         "invalid request",
+                         MAIL_SERVICE_PROXYMAP, dict->name, key);
+           case PROXY_STAT_DENY:
+               msg_fatal("%s service is not configured for table \"%s\"",
+                         MAIL_SERVICE_PROXYMAP, dict->name);
+           case PROXY_STAT_OK:
                return (STR(dict_proxy->result));
-           } else if (status == PROXY_STAT_FAIL) {
+           case PROXY_STAT_NOKEY:
                return (0);
-           } else if (status == PROXY_STAT_RETRY) {
+           case PROXY_STAT_RETRY:
                dict_errno = DICT_ERR_RETRY;
                return (0);
-           } else if (status == PROXY_STAT_BAD) {
-               msg_fatal("%s: %s lookup %s failed: bad request",
-                         myname, dict->name, key);
-           } else {
-               msg_warn("%s: %s lookup %s failed with unknown status %d",
-                        myname, dict->name, key, status);
+           default:
+               msg_warn("%s lookup failed for table \"%s\" key \"%s\": "
+                        "unexpected reply status %d",
+                        MAIL_SERVICE_PROXYMAP, dict->name, key, status);
            }
        }
        clnt_stream_recover(proxy_stream);
@@ -166,10 +172,10 @@ DICT   *dict_proxy_open(const char *map, int open_flags, int dict_flags)
     /*
      * Sanity checks.
      */
+    if (dict_flags & DICT_FLAG_NO_PROXY)
+       msg_fatal("%s: proxy map must not be used with this map type", map);
     if (open_flags != O_RDONLY)
        msg_fatal("%s: proxy map open requires O_RDONLY access mode", map);
-    if (dict_flags & DICT_FLAG_NO_PROXY)
-       msg_fatal("%s: proxy map is not allowed for this map type", map);
 
     /*
      * Local initialization.
@@ -201,7 +207,9 @@ DICT   *dict_proxy_open(const char *map, int open_flags, int dict_flags)
     }
 
     /*
-     * Establish initial contact and finalize the flags.
+     * Establish initial contact and get the map type specific flags.
+     * 
+     * XXX Should retrieve flags from local instance.
      */
     for (;;) {
        stream = clnt_stream_access(proxy_stream);
@@ -217,21 +225,26 @@ DICT   *dict_proxy_open(const char *map, int open_flags, int dict_flags)
                         ATTR_TYPE_END) != 2) {
            if (msg_verbose || (errno != EPIPE && errno != ENOENT))
                msg_warn("%s: service %s: %m", VSTREAM_PATH(stream), myname);
-       } else if (status == PROXY_STAT_OK) {
+       } else {
            if (msg_verbose)
                msg_info("%s: connect to map=%s status=%d server_flags=0%o",
                       myname, dict_proxy->dict.name, status, server_flags);
-           dict_proxy->dict.flags = dict_proxy->in_flags | server_flags;
-           break;
-       } else if (status == PROXY_STAT_BAD) {
-           msg_fatal("%s: %s connection request failed: bad request",
-                     myname, dict_proxy->dict.name);
-       } else {
-           msg_warn("%s: %s connection request failed with status %d",
-                    myname, dict_proxy->dict.name, status);
+           switch (status) {
+           case PROXY_STAT_BAD:
+               msg_fatal("%s open failed for table \"%s\": invalid request",
+                         MAIL_SERVICE_PROXYMAP, dict_proxy->dict.name);
+           case PROXY_STAT_DENY:
+               msg_fatal("%s service is not configured for table \"%s\"",
+                         MAIL_SERVICE_PROXYMAP, dict_proxy->dict.name);
+           case PROXY_STAT_OK:
+               dict_proxy->dict.flags = dict_proxy->in_flags | server_flags;
+               return (DICT_DEBUG (&dict_proxy->dict));
+           default:
+               msg_warn("%s open failed for table \"%s\": unexpected status %d",
+                     MAIL_SERVICE_PROXYMAP, dict_proxy->dict.name, status);
+           }
        }
        clnt_stream_recover(proxy_stream);
        sleep(1);                               /* XXX make configurable */
     }
-    return (DICT_DEBUG (&dict_proxy->dict));
 }
index 50932b0c4c92c8568e252a0dab44f335dc71e31d..ce49626094936479a69c9dbb696bc5ec0a99c8da 100644 (file)
@@ -29,10 +29,11 @@ extern DICT *dict_proxy_open(const char *, int, int);
 #define PROXY_REQ_OPEN         "open"
 #define PROXY_REQ_LOOKUP       "lookup"
 
-#define PROXY_STAT_OK          0
-#define PROXY_STAT_FAIL                1
-#define PROXY_STAT_BAD         2
-#define PROXY_STAT_RETRY       3
+#define PROXY_STAT_OK          0       /* operation succeeded */
+#define PROXY_STAT_NOKEY       1       /* requested key not found */
+#define PROXY_STAT_RETRY       2       /* try lookup again later */
+#define PROXY_STAT_BAD         3       /* invalid request parameter */
+#define PROXY_STAT_DENY                4       /* table not approved for proxying */
 
 /* LICENSE
 /* .ad
index 554e94a03f95179201761b7f4cd994e771878b76..9f8e01e41bec650fa59dc4b2cf7c69e1bb9e5e74 100644 (file)
@@ -1332,8 +1332,8 @@ extern int var_local_rcpt_code;
  /*
   * List of pre-approved maps that are OK to open with the proxymap service.
   */
-#define VAR_PROXYMAP_FILTER    "proxymap_filter"
-#define DEF_PROXYMAP_FILTER    "$" VAR_LOCAL_RCPT_MAPS \
+#define VAR_PROXY_READ_MAPS    "proxy_read_maps"
+#define DEF_PROXY_READ_MAPS    "$" VAR_LOCAL_RCPT_MAPS \
                                " $" VAR_MYDEST \
                                " $" VAR_VIRT_ALIAS_MAPS \
                                " $" VAR_VIRT_ALIAS_DOMS \
@@ -1346,7 +1346,7 @@ extern int var_local_rcpt_code;
                                " $" VAR_RCPT_CANON_MAPS \
                                " $" VAR_RELOCATED_MAPS \
                                " $" VAR_TRANSPORT_MAPS
-extern char *var_proxymap_filter;
+extern char *var_proxy_read_maps;
 
  /*
   * Other.
index 8c770247ecad3e64d087ee51f13692e902a537b7..59b18fdb25f9cc8bb4c38f43b7ed311062457950 100644 (file)
@@ -20,7 +20,7 @@
   * Patches change the patchlevel and the release date. Snapshots change the
   * release date only, unless they include the same bugfix as a patch release.
   */
-#define MAIL_RELEASE_DATE      "20030103"
+#define MAIL_RELEASE_DATE      "20030104"
 
 #define VAR_MAIL_VERSION       "mail_version"
 #define DEF_MAIL_VERSION       "2.0.0-" MAIL_RELEASE_DATE
index 41cd78584fd11aab43bce6b6c235f972e6d86e83..698617952d52e4aae5a0c9ef7e43a9774fcf3365 100644 (file)
@@ -184,22 +184,20 @@ void    resolve_clnt_query(const char *addr, RESOLVE_REPLY *reply)
 
     for (;;) {
        stream = clnt_stream_access(rewrite_clnt_stream);
+       errno = 0;
        if (attr_print(stream, ATTR_FLAG_NONE,
                       ATTR_TYPE_STR, MAIL_ATTR_REQ, RESOLVE_ADDR,
                       ATTR_TYPE_STR, MAIL_ATTR_ADDR, addr,
-                      ATTR_TYPE_END)
-           || vstream_fflush(stream)) {
-           if (msg_verbose || (errno != EPIPE && errno != ENOENT))
-               msg_warn("%s: bad write: %m", myname);
-       } else if (attr_scan(stream, ATTR_FLAG_STRICT,
+                      ATTR_TYPE_END) != 0
+           || attr_scan(stream, ATTR_FLAG_STRICT,
                       ATTR_TYPE_STR, MAIL_ATTR_TRANSPORT, reply->transport,
-                          ATTR_TYPE_STR, MAIL_ATTR_NEXTHOP, reply->nexthop,
-
-                          ATTR_TYPE_STR, MAIL_ATTR_RECIP, reply->recipient,
-                            ATTR_TYPE_NUM, MAIL_ATTR_FLAGS, &reply->flags,
-                            ATTR_TYPE_END) != 4) {
+                        ATTR_TYPE_STR, MAIL_ATTR_NEXTHOP, reply->nexthop,
+                        ATTR_TYPE_STR, MAIL_ATTR_RECIP, reply->recipient,
+                        ATTR_TYPE_NUM, MAIL_ATTR_FLAGS, &reply->flags,
+                        ATTR_TYPE_END) != 4) {
            if (msg_verbose || (errno != EPIPE && errno != ENOENT))
-               msg_warn("%s: bad read: %m", myname);
+               msg_warn("problem talking to service %s: %m",
+                        var_rewrite_service);
        } else {
            if (msg_verbose)
                msg_info("%s: `%s' -> t=`%s' h=`%s' r=`%s'",
@@ -212,7 +210,7 @@ void    resolve_clnt_query(const char *addr, RESOLVE_REPLY *reply)
            else
                break;
        }
-       sleep(10);                              /* XXX make configurable */
+       sleep(1);                               /* XXX make configurable */
        clnt_stream_recover(rewrite_clnt_stream);
     }
 
index ce7850d9ee2298d6e0384449f39537175ea6d011..24bb4d4326ac8a9e0466a2980b044c532aaaf067 100644 (file)
@@ -125,26 +125,25 @@ VSTRING *rewrite_clnt(const char *rule, const char *addr, VSTRING *result)
 
     for (;;) {
        stream = clnt_stream_access(rewrite_clnt_stream);
+       errno = 0;
        if (attr_print(stream, ATTR_FLAG_NONE,
                       ATTR_TYPE_STR, MAIL_ATTR_REQ, REWRITE_ADDR,
                       ATTR_TYPE_STR, MAIL_ATTR_RULE, rule,
                       ATTR_TYPE_STR, MAIL_ATTR_ADDR, addr,
-                      ATTR_TYPE_END),
-           vstream_fflush(stream)) {
+                      ATTR_TYPE_END) != 0
+           || attr_scan(stream, ATTR_FLAG_STRICT,
+                        ATTR_TYPE_STR, MAIL_ATTR_ADDR, result,
+                        ATTR_TYPE_END) != 1) {
            if (msg_verbose || (errno != EPIPE && errno != ENOENT))
-               msg_warn("%s: bad write: %m", myname);
-       } else if (attr_scan(stream, ATTR_FLAG_STRICT,
-                            ATTR_TYPE_STR, MAIL_ATTR_ADDR, result,
-                            ATTR_TYPE_END) != 1) {
-           if (msg_verbose || (errno != EPIPE && errno != ENOENT))
-               msg_warn("%s: bad read: %m", myname);
+               msg_warn("problem talking to service %s: %m",
+                        var_rewrite_service);
        } else {
            if (msg_verbose)
                msg_info("rewrite_clnt: %s: %s -> %s",
                         rule, addr, vstring_str(result));
            break;
        }
-       sleep(10);                              /* XXX make configurable */
+       sleep(1);                               /* XXX make configurable */
        clnt_stream_recover(rewrite_clnt_stream);
     }
 
index 878df8f9e1d66d6e3174fa38b15181d59e5d30c6..dd7a09156ac1dd93db4d3c38b38cb49daa81c5ba 100644 (file)
@@ -117,24 +117,19 @@ int     verify_clnt_query(const char *addr, int *addr_status, VSTRING *why)
      */
     for (;;) {
        stream = clnt_stream_access(vrfy_clnt);
+       errno = 0;
        if (attr_print(stream, ATTR_FLAG_NONE,
                       ATTR_TYPE_STR, MAIL_ATTR_REQ, VRFY_REQ_QUERY,
                       ATTR_TYPE_STR, MAIL_ATTR_ADDR, addr,
                       ATTR_TYPE_END) != 0
-           || vstream_fflush(stream)) {
-           if (msg_verbose || (errno != EPIPE && errno != ENOENT)) {
-               msg_warn("service %s: bad write: %m", var_verify_service);
-               sleep(10);                      /* XXX make configurable */
-           }
-       } else if (attr_scan(stream, ATTR_FLAG_MISSING,
-                          ATTR_TYPE_NUM, MAIL_ATTR_STATUS, &request_status,
-                         ATTR_TYPE_NUM, MAIL_ATTR_ADDR_STATUS, addr_status,
-                            ATTR_TYPE_STR, MAIL_ATTR_WHY, why,
-                            ATTR_TYPE_END) != 3) {
-           if (msg_verbose || (errno != EPIPE && errno != ENOENT)) {
-               msg_warn("service %s: bad read: %m", var_verify_service);
-               sleep(10);                      /* XXX make configurable */
-           }
+           || attr_scan(stream, ATTR_FLAG_MISSING,
+                        ATTR_TYPE_NUM, MAIL_ATTR_STATUS, &request_status,
+                        ATTR_TYPE_NUM, MAIL_ATTR_ADDR_STATUS, addr_status,
+                        ATTR_TYPE_STR, MAIL_ATTR_WHY, why,
+                        ATTR_TYPE_END) != 3) {
+           if (msg_verbose || (errno != EPIPE && errno != ENOENT))
+               msg_warn("problem talking to service %s: %m",
+                        var_verify_service);
        } else {
            break;
        }
@@ -181,25 +176,19 @@ int     verify_clnt_vupdate(const char *addr, int addr_status,
     vstring_vsprintf(text, format, ap);
     for (;;) {
        stream = clnt_stream_access(vrfy_clnt);
+       errno = 0;
        if (attr_print(stream, ATTR_FLAG_NONE,
                       ATTR_TYPE_STR, MAIL_ATTR_REQ, VRFY_REQ_UPDATE,
                       ATTR_TYPE_STR, MAIL_ATTR_ADDR, addr,
                       ATTR_TYPE_NUM, MAIL_ATTR_ADDR_STATUS, addr_status,
                       ATTR_TYPE_STR, MAIL_ATTR_WHY, vstring_str(text),
                       ATTR_TYPE_END) != 0
-           || vstream_fflush(stream)) {
-           if (msg_verbose || (errno != EPIPE && errno != ENOENT)) {
-               msg_warn("service %s: bad write: %m", var_verify_service);
-               msg_warn("service %s: bad write: %m", var_verify_service);
-               sleep(10);                      /* XXX make configurable */
-           }
-       } else if (attr_scan(stream, ATTR_FLAG_MISSING,
-                          ATTR_TYPE_NUM, MAIL_ATTR_STATUS, &request_status,
-                            ATTR_TYPE_END) != 1) {
-           if (msg_verbose || (errno != EPIPE && errno != ENOENT)) {
-               msg_warn("service %s: bad read: %m", var_verify_service);
-               sleep(10);                      /* XXX make configurable */
-           }
+           || attr_scan(stream, ATTR_FLAG_MISSING,
+                        ATTR_TYPE_NUM, MAIL_ATTR_STATUS, &request_status,
+                        ATTR_TYPE_END) != 1) {
+           if (msg_verbose || (errno != EPIPE && errno != ENOENT))
+               msg_warn("problem talking to service %s: %m",
+                        var_verify_service);
        } else {
            break;
        }
index c911737ec58ea08c2aef63155db6013ac9492662..fb05dc7d0d8e0bd6f05b31c926f191a0f121e792 100644 (file)
 /*     named dictionaries.
 /*     The result is a handle that must be specified along with all
 /*     other virtual8_maps_xxx() operations.
-/*     See dict_open(3) for a description of flags. virtual8_maps_create()
-/*     implicitly sets the DICT_FLAG_NO_REGSUB flag in order to disable
-/*     regular expression substitution into the lookup result, and
-/*     implicitly sets the DICT_FLAG_NO_PROXY flag in order to disable
-/*     lookup of sensitive information via an untrusted process.
+/*     See dict_open(3) for a description of flags.
 /*
 /*     virtual8_maps_find() searches the specified list of dictionaries
 /*     in the specified order for the named key. The result is in
index 2cf89f6c84ec207ce70d5763823c76ce6e020b79..67c5df910299233f58a178b730368bd69fc198b3 100644 (file)
@@ -20,8 +20,7 @@
   * External interface.
   */
 #define virtual8_maps_create(title, map_names, flags) \
-       maps_create((title), (map_names), \
-       (flags) | DICT_FLAG_NO_REGSUB | DICT_FLAG_NO_PROXY)
+       maps_create((title), (map_names), (flags))
 extern const char *virtual8_maps_find(MAPS *, const char *);
 #define virtual8_maps_free(maps)       maps_free((maps))
 
index 7b45845474ae701ee915ad674e935797fe587cbe..d6019f441f6f453a925daf9821a2993bb94d466e 100644 (file)
@@ -696,10 +696,8 @@ static void pre_init(char *unused_name, char **unused_argv)
                      VAR_MAILBOX_LIMIT, VAR_MESSAGE_LIMIT);
        set_file_limit(var_mailbox_limit);
     }
-#define INSECURE_DICT_FLAGS (DICT_FLAG_NO_REGSUB | DICT_FLAG_NO_PROXY)
-
     alias_maps = maps_create("aliases", var_alias_maps,
-                            DICT_FLAG_LOCK | INSECURE_DICT_FLAGS);
+                            DICT_FLAG_LOCK | DICT_FLAG_PARANOID);
 }
 
 /* main - pass control to the single-threaded skeleton */
index d2950752974e1311ec6a02727c49dff0313dce0e..871200efd3c706ec4506c0d8652a6db901a5ac24 100644 (file)
 /* .IP \(bu
 /*     To overcome chroot restrictions. For example, a chrooted SMTP
 /*     server needs access to the system passwd file in order to
-/*     reject mail for non-existent local addresses.
-/*     The solution is to specify:
+/*     reject mail for non-existent local addresses, but it is not
+/*     practical to maintain a copy of the passwd file in the chroot
+/*     jail.  The solution:
 /* .sp
 /*     local_recipient_maps =
 /* .ti +4
 /*     proxy:unix:passwd.byname $alias_maps
 /* .IP \(bu
 /*     To consolidate the number of open lookup tables by sharing
-/*     one open table among multiple processes. For example, to avoid
-/*     problems due to "too many connections" to, e.g., mysql servers,
-/*     specify:
+/*     one open table among multiple processes. For example, making
+/*     mysql connections from every Postfix daemon process results
+/*     in "too many connections" errors. The solution:
 /* .sp
 /*     virtual_alias_maps =
 /* .ti +4
 /*     proxy:mysql:/etc/postfix/virtual.cf
-/* PROXYMAP SERVICES
-/* .ad
-/* .fi
+/* .sp
+/*     The total number of connections is limited by the number of
+/*     proxymap server server processes.
+/* .PP
 /*     The proxymap server implements the following requests:
 /* .IP "\fBPROXY_REQ_OPEN\fI maptype:mapname flags\fR"
 /*     Open the table with type \fImaptype\fR and name \fImapname\fR,
 /*     as controlled by \fIflags\fR.
-/*     The reply is the request completion status code and the
+/*     The reply is the request completion status code (below) and the
 /*     map type dependent flags.
 /* .IP "\fBPROXY_REQ_LOOKUP\fI maptype:mapname flags key\fR"
 /*     Look up the data stored under the requested key.
-/*     The reply is the request completion status code and
+/*     The reply is the request completion status code (below) and
 /*     the lookup result value.
 /*     The \fImaptype:mapname\fR and \fIflags\fR are the same
 /*     as with the \fBPROXY_REQ_OPEN\fR request.
 /*
 /*     The request completion status code is one of:
 /* .IP \fBPROXY_STAT_OK\fR
-/*     The requested table or lookup key was found.
-/* .IP \fBPROXY_STAT_FAIL\fR
-/*     The requested table or lookup key does not exist.
+/*     The specified table was opened, or the requested entry was found.
+/* .IP \fBPROXY_STAT_NOKEY\fR
+/*     The requested table entry was not found.
 /* .IP \fBPROXY_STAT_BAD\fR
 /*     The request was rejected (bad request parameter value).
 /* .IP \fBPROXY_STAT_RETRY\fR
-/*     The request was not completed.
-/* MASTER INTERFACE
+/*     The lookup request could not be completed.
+/* .IP \fBPROXY_STAT_DENY\fR
+/*     The specified table was not approved for access via the
+/*     proxymap service.
+/* SERVER PROCESS MANAGEMENT
 /* .ad
 /* .fi
 /*     The proxymap servers run under control by the Postfix master
 /*     server.  Each server can handle multiple simultaneous connections.
 /*     When all servers are busy while a client connects, the master
-/*     creates a new proxymap server process, provided that the proxymap 
+/*     creates a new proxymap server process, provided that the proxymap
 /*     server process limit is not exceeded.
-/*     Each proxymap server terminates after serving \fB$max_use\fR clients
-/*     or after \fB$max_idle\fR seconds of idle time.
+/*     Each proxymap server stops accepting new connections after serving
+/*     \fB$max_use\fR clients or terminates after \fB$max_idle\fR seconds
+/*     of idle time.
 /* SECURITY
 /* .ad
 /* .fi
-/*     The proxymap server is not security-sensitive. It opens only
-/*     tables that are approved via the \fBproxymap_filter\fR
-/*     configuration parameter, does not talk to users, and
-/*     can run at fixed low privilege, chrooted or not.
+/*     The proxymap server opens only tables that are approved via the
+/*     \fBproxy_read_maps\fR configuration parameter, does not talk to
+/*     users, and can run at fixed low privilege, chrooted or not.
+/*
+/*     The proxymap server is not a trusted daemon process, and must
+/*     not be used to look up sensitive information such as user or
+/*     group IDs, mailbox file/directory names or external commands.
 /* DIAGNOSTICS
 /*     Problems and transactions are logged to \fBsyslogd\fR(8).
 /* BUGS
 /*     The following main.cf parameters are especially relevant
 /*     to this program. Use the \fBpostfix reload\fR command
 /*     after a configuration change.
-/* .IP \fBproxymap_filter\fR
+/* .IP \fBproxy_read_maps\fR
 /*     A list of zero or more parameter values that may contain
-/*     Postfix lookup table references. Only table references that
-/*     begin with \fBproxy:\fR are approved for access via the
-/*     proxymap server.
+/*     references to Postfix lookup tables. Only table references
+/*     that begin with \fBproxy:\fR are approved for read-only
+/*     access via the proxymap server.
 /* SEE ALSO
 /*     dict_proxy(3) proxy map client
 /* LICENSE
@@ -148,20 +157,20 @@ char   *var_send_canon_maps;
 char   *var_rcpt_canon_maps;
 char   *var_relocatedmaps;
 char   *var_transport_maps;
-char   *var_proxymap_filter;
+char   *var_proxy_read_maps;
 
  /*
   * The pre-approved, pre-parsed list of maps.
   */
-static HTABLE *proxymap_filter;
+static HTABLE *proxy_read_maps;
 
  /*
   * Shared and static to reduce memory allocation overhead.
   */
 static VSTRING *request;
+static VSTRING *request_map;
+static VSTRING *request_key;
 static VSTRING *map_type_name_flags;
-static VSTRING *map_type_name;
-static VSTRING *key;
 
  /*
   * Silly little macros.
@@ -171,13 +180,13 @@ static VSTRING *key;
 
 /* proxy_map_find - look up or open table */
 
-static DICT *proxy_map_find(const char *map_type_name, int dict_flags)
+static DICT *proxy_map_find(const char *map_type_name, int request_flags)
 {
     DICT   *dict;
 
 #define PROXY_COLON    DICT_TYPE_PROXY ":"
 #define PROXY_COLON_LEN        (sizeof(PROXY_COLON) - 1)
-#define OPEN_FLAGS     O_RDONLY
+#define READ_OPEN_FLAGS        O_RDONLY
 
     /*
      * Canonicalize the map name. If the map is not on the approved list,
@@ -185,8 +194,10 @@ static DICT *proxy_map_find(const char *map_type_name, int dict_flags)
      */
     while (strncmp(map_type_name, PROXY_COLON, PROXY_COLON_LEN) == 0)
        map_type_name += PROXY_COLON_LEN;
-    if (htable_locate(proxymap_filter, map_type_name) == 0) {
-       msg_warn("request for unapproved map: %s", map_type_name);
+    if (htable_locate(proxy_read_maps, map_type_name) == 0) {
+       msg_warn("request for unapproved table: \"%s\"", map_type_name);
+       msg_warn("to approve a table for %s access, specify it in %s with %s",
+                MAIL_SERVICE_PROXYMAP, MAIN_CONF_FILE, VAR_PROXY_READ_MAPS);
        return (0);
     }
 
@@ -194,9 +205,9 @@ static DICT *proxy_map_find(const char *map_type_name, int dict_flags)
      * Open one instance of a map for each combination of name+flags.
      */
     vstring_sprintf(map_type_name_flags, "%s:%o",
-                   map_type_name, dict_flags);
+                   map_type_name, request_flags);
     if ((dict = dict_handle(STR(map_type_name_flags))) == 0)
-       dict = dict_open(map_type_name, OPEN_FLAGS, dict_flags);
+       dict = dict_open(map_type_name, READ_OPEN_FLAGS, request_flags);
     if (dict == 0)
        msg_panic("proxy_map_find: dict_open null result");
     dict_register(STR(map_type_name_flags), dict);
@@ -207,35 +218,40 @@ static DICT *proxy_map_find(const char *map_type_name, int dict_flags)
 
 static void proxymap_lookup_service(VSTREAM *client_stream)
 {
-    int     status = PROXY_STAT_BAD;
+    int     request_flags;
     DICT   *dict;
-    const char *value = "";
-    int     dict_flags;
+    const char *reply_value;
+    int     reply_status;
 
+    /*
+     * Process the request.
+     */
     if (attr_scan(client_stream, ATTR_FLAG_STRICT,
-                 ATTR_TYPE_STR, MAIL_ATTR_TABLE, map_type_name,
-                 ATTR_TYPE_NUM, MAIL_ATTR_FLAGS, &dict_flags,
-                 ATTR_TYPE_STR, MAIL_ATTR_KEY, key,
-                 ATTR_TYPE_END) == 3
-       && (dict = proxy_map_find(STR(map_type_name), dict_flags)) != 0) {
-
-       if ((value = dict_get(dict, STR(key))) != 0) {
-           status = PROXY_STAT_OK;
-       } else if (dict_errno == 0) {
-           status = PROXY_STAT_FAIL;
-           value = "";
-       } else {
-           status = PROXY_STAT_RETRY;
-           value = "";
-       }
+                 ATTR_TYPE_STR, MAIL_ATTR_TABLE, request_map,
+                 ATTR_TYPE_NUM, MAIL_ATTR_FLAGS, &request_flags,
+                 ATTR_TYPE_STR, MAIL_ATTR_KEY, request_key,
+                 ATTR_TYPE_END) != 3) {
+       reply_status = PROXY_STAT_BAD;
+       reply_value = "";
+    } else if ((dict = proxy_map_find(STR(request_map), request_flags)) == 0) {
+       reply_status = PROXY_STAT_DENY;
+       reply_value = "";
+    } else if ((reply_value = dict_get(dict, STR(request_key))) != 0) {
+       reply_status = PROXY_STAT_OK;
+    } else if (dict_errno == 0) {
+       reply_status = PROXY_STAT_NOKEY;
+       reply_value = "";
+    } else {
+       reply_status = PROXY_STAT_RETRY;
+       reply_value = "";
     }
 
     /*
      * Respond to the client.
      */
     attr_print(client_stream, ATTR_FLAG_NONE,
-              ATTR_TYPE_NUM, MAIL_ATTR_STATUS, status,
-              ATTR_TYPE_STR, MAIL_ATTR_VALUE, value,
+              ATTR_TYPE_NUM, MAIL_ATTR_STATUS, reply_status,
+              ATTR_TYPE_STR, MAIL_ATTR_VALUE, reply_value,
               ATTR_TYPE_END);
 }
 
@@ -243,27 +259,34 @@ static void proxymap_lookup_service(VSTREAM *client_stream)
 
 static void proxymap_open_service(VSTREAM *client_stream)
 {
-    int     dict_flags;
+    int     request_flags;
     DICT   *dict;
-    int     status = PROXY_STAT_BAD;
-    int     flags = 0;
+    int     reply_status;
+    int     reply_flags;
 
+    /*
+     * Process the request.
+     */
     if (attr_scan(client_stream, ATTR_FLAG_STRICT,
-                 ATTR_TYPE_STR, MAIL_ATTR_TABLE, map_type_name,
-                 ATTR_TYPE_NUM, MAIL_ATTR_FLAGS, &dict_flags,
-                 ATTR_TYPE_END) == 2
-       && (dict = proxy_map_find(STR(map_type_name), dict_flags)) != 0) {
-
-       status = PROXY_STAT_OK;
-       flags = dict->flags;
+                 ATTR_TYPE_STR, MAIL_ATTR_TABLE, request_map,
+                 ATTR_TYPE_NUM, MAIL_ATTR_FLAGS, &request_flags,
+                 ATTR_TYPE_END) != 2) {
+       reply_status = PROXY_STAT_BAD;
+       reply_flags = 0;
+    } else if ((dict = proxy_map_find(STR(request_map), request_flags)) == 0) {
+       reply_status = PROXY_STAT_DENY;
+       reply_flags = 0;
+    } else {
+       reply_status = PROXY_STAT_OK;
+       reply_flags = dict->flags;
     }
 
     /*
      * Respond to the client.
      */
     attr_print(client_stream, ATTR_FLAG_NONE,
-              ATTR_TYPE_NUM, MAIL_ATTR_STATUS, status,
-              ATTR_TYPE_NUM, MAIL_ATTR_FLAGS, flags,
+              ATTR_TYPE_NUM, MAIL_ATTR_STATUS, reply_status,
+              ATTR_TYPE_NUM, MAIL_ATTR_FLAGS, reply_flags,
               ATTR_TYPE_END);
 }
 
@@ -311,28 +334,41 @@ static void post_jail_init(char *unused_name, char **unused_argv)
     char   *bp;
     char   *type_name;
 
+    /*
+     * Pre-allocate buffers.
+     */
     request = vstring_alloc(10);
-    map_type_name = vstring_alloc(10);
+    request_map = vstring_alloc(10);
+    request_key = vstring_alloc(10);
     map_type_name_flags = vstring_alloc(10);
-    key = vstring_alloc(10);
 
     /*
      * Prepare the pre-approved list of proxied tables.
      */
-    saved_filter = bp = mystrdup(var_proxymap_filter);
-    proxymap_filter = htable_create(13);
+    saved_filter = bp = mystrdup(var_proxy_read_maps);
+    proxy_read_maps = htable_create(13);
     while ((type_name = mystrtok(&bp, sep)) != 0) {
        if (strncmp(type_name, PROXY_COLON, PROXY_COLON_LEN))
            continue;
        do {
            type_name += PROXY_COLON_LEN;
        } while (!strncmp(type_name, PROXY_COLON, PROXY_COLON_LEN));
-       if (htable_find(proxymap_filter, type_name) == 0)
-           (void) htable_enter(proxymap_filter, type_name, (char *) 0);
+       if (htable_locate(proxy_read_maps, type_name) == 0)
+           (void) htable_enter(proxy_read_maps, type_name, (char *) 0);
     }
     myfree(saved_filter);
 }
 
+/* pre_accept - see if tables have changed */
+
+static void pre_accept(char *unused_name, char **unused_argv)
+{
+    if (dict_changed()) {
+       msg_info("some lookup table has changed -- restarting");
+       exit(0);
+    }
+}
+
 /* main - pass control to the multi-threaded skeleton */
 
 int     main(int argc, char **argv)
@@ -350,12 +386,13 @@ int     main(int argc, char **argv)
        VAR_RCPT_CANON_MAPS, DEF_RCPT_CANON_MAPS, &var_rcpt_canon_maps, 0, 0,
        VAR_RELOCATED_MAPS, DEF_RELOCATED_MAPS, &var_relocatedmaps, 0, 0,
        VAR_TRANSPORT_MAPS, DEF_TRANSPORT_MAPS, &var_transport_maps, 0, 0,
-       VAR_PROXYMAP_FILTER, DEF_PROXYMAP_FILTER, &var_proxymap_filter, 0, 0,
+       VAR_PROXY_READ_MAPS, DEF_PROXY_READ_MAPS, &var_proxy_read_maps, 0, 0,
        0,
     };
 
     multi_server_main(argc, argv, proxymap_service,
                      MAIL_SERVER_STR_TABLE, str_table,
                      MAIL_SERVER_POST_INIT, post_jail_init,
+                     MAIL_SERVER_PRE_ACCEPT, pre_accept,
                      0);
 }
index b69f482b04d61b8c089c1232f6410dc4af4d62ca..60948ec95a181f8c2c8dc7d89b2c89968c0e9afb 100644 (file)
 /* .IP \fIrecipient\fR
 /*     The envelope recipient address that is passed on to \fInexthop\fR.
 /* .RE
-/* .PP
-/*     \fBtrivial-rewrite\fR servers run under control by the Postfix master
-/*     server. Each server can handle multiple simultaneous connections.
-/*     When all servers are busy while a client connects, a new server
-/*     process is created, provided that the trivial-rewrite server
-/*     process limit is not exceeded.
-/*     Each server terminates after serving \fB$max_use\fR clients
-/*     or after \fB$max_idle\fR seconds of idle time.
 /* DEFAULT DELIVERY METHODS
 /* .ad
 /* .fi
 /*     This overrides the optional nexthop information that is specified
 /*     with \fB$relayhost\fR.
 /*     The default nexthop is the recipient domain.
+/* SERVER PROCESS MANAGEMENT
+/* .ad
+/* .fi
+/*     The trivial-rewrite servers run under control by the Postfix master
+/*     server.  Each server can handle multiple simultaneous connections.
+/*     When all servers are busy while a client connects, the master
+/*     creates a new server process, provided that the trivial-rewrite
+/*     server process limit is not exceeded.
+/*     Each trivial-rewrite server stops accepting new connections after
+/*     serving \fB$max_use\fR clients or terminates after \fB$max_idle\fR
+/*     seconds of idle time.
 /* STANDARDS
 /* .ad
 /* .fi
index 546420dd2a9a11f1401c0629240103214b2e0989..6f30e2fd7adce7f6a451307705cf6523c3df9dd8 100644 (file)
@@ -58,10 +58,11 @@ extern DICT *dict_debug(DICT *);
 #define DICT_FLAG_SYNC_UPDATE  (1<<8)  /* if file, sync updates */
 #define DICT_FLAG_DEBUG                (1<<9)  /* log access */
 #define DICT_FLAG_FOLD_KEY     (1<<10) /* lowercase the lookup key */
-
 #define DICT_FLAG_NO_REGSUB    (1<<11) /* no lhs->rhs regexp substitution */
 #define DICT_FLAG_NO_PROXY     (1<<12) /* no proxy mapping */
 
+#define DICT_FLAG_PARANOID     (DICT_FLAG_NO_REGSUB | DICT_FLAG_NO_PROXY)
+
 extern int dict_unknown_allowed;
 extern int dict_errno;
 
index 2f50076fe625b2848ebd794304b6157f1cc45762..f949502835d6ee9bdbc25d0c641165f511aa50d8 100644 (file)
 /* .IP DICT_FLAG_NO_REGSUB
 /*      Disallow regular expression substitution from left-hand side data 
 /*     into the right-hand side.
+/* .IP DICT_FLAG_NO_PROXY
+/*     Disallow access through the \fBproxymap\fR service.
+/* .IP DICT_FLAG_PARANOID
+/*     A combination of all the paranoia flags: DICT_FLAG_NO_REGSUB
+/*     and DICT_FLAG_NO_PROXY.
 /* .PP
 /*     Specify DICT_FLAG_NONE for no special processing.
 /*
index 22c59440ca76416114c3771721906596fae6a87c..5cff4514075005c507d0397395195f53e0d7cb62 100644 (file)
@@ -640,8 +640,11 @@ static int vstream_buf_get_ready(VBUF *bp)
      * allocation gives the application a chance to override the default
      * buffering policy.
      */
-    if (bp->data == 0)
+    if (bp->data == 0) {
        vstream_buf_alloc(bp, VSTREAM_BUFSIZE);
+       if (bp->flags & VSTREAM_FLAG_DOUBLE) 
+           VSTREAM_SAVE_STATE(stream, read_buf, read_fd);
+    }
 
     /*
      * If the stream is double-buffered and the write buffer is not empty,
@@ -724,6 +727,8 @@ static int vstream_buf_put_ready(VBUF *bp)
      */
     if (bp->data == 0) {
        vstream_buf_alloc(bp, VSTREAM_BUFSIZE);
+       if (bp->flags & VSTREAM_FLAG_DOUBLE) 
+           VSTREAM_SAVE_STATE(stream, write_buf, write_fd);
     } else if (bp->cnt <= 0) {
        if (VSTREAM_FFLUSH_SOME(stream))
            return (VSTREAM_EOF);
index 49ed051dfbcc520d866a418518ffd287b2f34673..e0896f0b0418086f0c06b013b156d45c30714605 100644 (file)
@@ -413,15 +413,15 @@ static void post_init(char *unused_name, char **unused_argv)
 
     virtual_mailbox_maps =
        virtual8_maps_create(VAR_VIRT_MAILBOX_MAPS, var_virt_mailbox_maps,
-                            DICT_FLAG_LOCK);
+                            DICT_FLAG_LOCK | DICT_FLAG_PARANOID);
 
     virtual_uid_maps =
        virtual8_maps_create(VAR_VIRT_UID_MAPS, var_virt_uid_maps,
-                            DICT_FLAG_LOCK);
+                            DICT_FLAG_LOCK | DICT_FLAG_PARANOID);
 
     virtual_gid_maps =
        virtual8_maps_create(VAR_VIRT_GID_MAPS, var_virt_gid_maps,
-                            DICT_FLAG_LOCK);
+                            DICT_FLAG_LOCK | DICT_FLAG_PARANOID);
 
     virtual_mbox_lock_mask = mbox_lock_mask(var_virt_mailbox_lock);
 }