Dear all,

Just to wind this up and record the outcome for anyone now or in the future
searching for a solution to a similar problem…

Our underlying problem was that when Exim tries to bind using ldapauth to
our LDAP server to verify a username/password combination it's getting
(49) when the username doesn't exist.

My colleagues here wonder if this might be because we're using the Sun LDAP
server instead of OpenLDAP and its behaviour is different. I confess I'm
disappointed that Exim only returns a FAIL for the LDAP_INVALID_CREDENTIALS
error; when the username doesn't exist in our LDAP server, so its object
isn't present and can't possibly bind successfully, Exim instead gives an
expansion error.

Sadly getting an expansion error from ldapauth in server_condition causes
the authenticator to defer. This means a different SMTP response code and
textual string is returned to the client from the one returned when the
username exists but the password supplied is incorrect. Therefore the
technique suggested in the *Specification* to use ldapauth alone to
validate username/password pairs leaks information to the client with some
LDAP servers/setups about whether the username exists or not. I and others
consider this a security concern so should be avoided.

Thankfully Jeremy suggested I explicitly check for a valid username before
checking the password. At first I thought this was a non-starter as it
would require a service account on our LDAP server to search the username
tree, and the team who manage the service diligently guard such accounts.
Fortunately a colleague reminded me that our usernames are valid on our
mail gateways: their accounts just can't get sessions. This let me use
Exim's passwd lookup to check whether the username exists and then, only if
it does, validate the password using ldapauth. My revised server_condition
for the LOGIN authenticator now looks like this:

server_condition = ${if and{ \
                             { def:auth1 } \
                             { def:auth2 } \
                             { bool{ \
                                     ${lookup {$auth1} lsearch
{/etc/exim4/cfg.d/passwords-for-auth-smtp} \
                                        { ${if crypteq {$auth2}
{\{sha1\}$value}} } \
                                        { ${if and{ \
                                                    { bool_lax{ ${lookup
passwd {${quote_passwd:$auth1}}} } } \
                                                    { ldapauth \


pass=${quote:$auth2} \
                                                        nettime=10 \
                                                        time=7 \
                                                        ldap://} } \
                                                  }}} \
                                      } \
                                   }} \

As usual, my apologies about the long lines: I'm using a 27 inch screen so
have a big terminal window!

I appreciate the suggestions people made to use BlockCracking
<> and it looks wonderful,
although perhaps over complex for our legacy mail gateways. However I'm
also not sure it would be suitable in our current environment. We have some
legitimate users here who are using external service providers who relay
the outgoing messages through our gateways using AuthSMTP. Unfortunately
their data is not very "clean" at the moment and can include syntactically
incorrect, invalid or obsolete addresses. As I understand it this would
trigger the BlockCracking defences because they try to send to more
than *N* bad
addresses within a time period: something that would impact the messages to
the valid addresses. (Yes, they're working on cleaning the data now I've
brought the problem to their attention! :-)

Many thanks to all who contributed their thoughts!
Mike B-)

Systems Administrator & Change Manager
IT Services, University of York, Heslington, York YO10 5DD, UK
Tel: +44-(0)1904-323811

## List details at
## Exim details at
## Please use the Wiki with this list -

Reply via email to