On Tue, Sep 18, 2018 at 10:55:50PM -0700, Ryan Tandy wrote:
>There is some EAGAIN handling conditional on LDAP_USE_NON_BLOCKING_TLS
>which itself is behind LDAP_DEVEL. However this code is meant for
>non-blocking sockets, and in my case it ends up stuck in poll()
>waiting for a notification that never arrives.
This turned out to be because the fd and timeout fields are only
initialized when timeout is configured and the non-blocking behaviour
was triggered because of it. Otherwise the code simply doesn't
anticipate EAGAIN could be returned and the behaviour is more or less
undefined; it ends up calling poll() with fd = -1 and a garbage timeout.
>It's possible that what I actually want here is a (ret > 0) case in
>ldap_int_tls_start for when LDAP_USE_NON_BLOCKING_TLS is absent and
>ldap_int_tls_connect returns 1. (I'd also need to adapt the
>non-blocking path to be able to handle a blocking socket as well.)
More precisely, what I actually want is a (ret > 0) case that is used
unless both USE_NON_BLOCKING_TLS is true and a timeout is configured.
If we added to ber_sockbuf_ctrl() the ability to query whether the
socket is non-blocking, for GnuTLS at least we could bypass poll() and
go straight back into ldap_int_tls_connect(). However I don't see a lot
of benefit to this as long as calling poll() on a blocking socket has no
downside.