/*
Bacula® - The Network Backup Solution
- Copyright (C) 2005-2007 Free Software Foundation Europe e.V.
+ Copyright (C) 2005-2008 Free Software Foundation Europe e.V.
The main author of Bacula is Kern Sibbald, with contributions from
many others, a complete list can be found in the file AUTHORS.
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301, USA.
- Bacula® is a registered trademark of John Walker.
+ Bacula® is a registered trademark of Kern Sibbald.
The licensor of Bacula is the Free Software Foundation Europe
(FSFE), Fiduciary Program, Sumatrastrasse 25, 8006 Zürich,
Switzerland, email:ftf@fsfeurope.org.
#include "bacula.h"
#include <assert.h>
-extern time_t watchdog_time;
#ifdef HAVE_TLS /* Is TLS enabled? */
X509_NAME_oneline(X509_get_issuer_name(cert), issuer, 256);
X509_NAME_oneline(X509_get_subject_name(cert), subject, 256);
- Jmsg5(get_jcr_from_tid(), M_ERROR, 0, _("Error with certificate at depth: %d, issuer = %s,"
- " subject = %s, ERR=%d:%s\n"), depth, issuer,
- subject, err, X509_verify_cert_error_string(err));
+ Jmsg5(NULL, M_ERROR, 0, _("Error with certificate at depth: %d, issuer = %s,"
+ " subject = %s, ERR=%d:%s\n"), depth, issuer,
+ subject, err, X509_verify_cert_error_string(err));
}
}
} else if (verify_peer) {
/* At least one CA is required for peer verification */
- Jmsg0(get_jcr_from_tid(), M_ERROR, 0, _("Either a certificate file or a directory must be"
+ Jmsg0(NULL, M_ERROR, 0, _("Either a certificate file or a directory must be"
" specified as a verification store\n"));
goto err;
}
}
if (SSL_CTX_set_cipher_list(ctx->openssl, TLS_DEFAULT_CIPHERS) != 1) {
- Jmsg0(get_jcr_from_tid(), M_ERROR, 0,
+ Jmsg0(NULL, M_ERROR, 0,
_("Error setting cipher list, no valid ciphers available\n"));
goto err;
}
* Returns: true on success
* false on failure
*/
-bool tls_postconnect_verify_cn(TLS_CONNECTION *tls, alist *verify_list)
+bool tls_postconnect_verify_cn(JCR *jcr, TLS_CONNECTION *tls, alist *verify_list)
{
SSL *ssl = tls->openssl;
X509 *cert;
/* Check if peer provided a certificate */
if (!(cert = SSL_get_peer_certificate(ssl))) {
- Jmsg0(get_jcr_from_tid(), M_ERROR, 0, _("Peer failed to present a TLS certificate\n"));
+ Qmsg0(jcr, M_ERROR, 0, _("Peer failed to present a TLS certificate\n"));
return false;
}
* Returns: true on success
* false on failure
*/
-bool tls_postconnect_verify_host(TLS_CONNECTION *tls, const char *host)
+bool tls_postconnect_verify_host(JCR *jcr, TLS_CONNECTION *tls, const char *host)
{
SSL *ssl = tls->openssl;
X509 *cert;
/* Check if peer provided a certificate */
if (!(cert = SSL_get_peer_certificate(ssl))) {
- Jmsg1(get_jcr_from_tid(), M_ERROR, 0,
+ Qmsg1(jcr, M_ERROR, 0,
_("Peer %s failed to present a TLS certificate\n"), host);
return false;
}
/* start timer */
bsock->timer_start = watchdog_time;
- bsock->set_timed_out(false);
+ bsock->clear_timed_out();
for (;;) {
if (server) {
tv.tv_sec = 10;
tv.tv_usec = 0;
/* Block until we can read */
- select(fdmax, &fdset, NULL, &fdset, &tv);
+ select(fdmax, &fdset, NULL, NULL, &tv);
break;
case SSL_ERROR_WANT_WRITE:
/* If we timeout of a select, this will be unset */
tv.tv_sec = 10;
tv.tv_usec = 0;
/* Block until we can write */
- select(fdmax, NULL, &fdset, &fdset, &tv);
+ select(fdmax, NULL, &fdset, NULL, &tv);
break;
default:
- /* Socket Error Occured */
+ /* Socket Error Occurred */
openssl_post_errors(M_ERROR, _("Connect failure"));
stat = false;
goto cleanup;
* The first time to initiate the shutdown handshake, and the second to
* receive the peer's reply.
*
- * However, it is valid to close the SSL connection after the initial
- * shutdown notification is sent to the peer, without waiting for the
- * peer's reply, as long as you do not plan to re-use that particular
- * SSL connection object.
- *
- * Because we do not re-use SSL connection objects, I do not bother
- * calling SSL_shutdown a second time.
- *
* In addition, if the underlying socket is blocking, SSL_shutdown()
* will not return until the current stage of the shutdown process has
* completed or an error has occured. By setting the socket blocking
* we can avoid the ugly for()/switch()/select() loop.
*/
int err;
- int flags;
+
+ btimer_t *tid;
/* Set socket blocking for shutdown */
- flags = bsock->set_blocking();
+ bsock->set_blocking();
+ tid = start_bsock_timer(bsock, 60 * 2);
err = SSL_shutdown(bsock->tls->openssl);
+ stop_bsock_timer(tid);
+ if (err == 0) {
+ /* Complete shutdown */
+ tid = start_bsock_timer(bsock, 60 * 2);
+ err = SSL_shutdown(bsock->tls->openssl);
+ stop_bsock_timer(tid);
+ }
+
switch (SSL_get_error(bsock->tls->openssl, err)) {
case SSL_ERROR_NONE:
openssl_post_errors(M_ERROR, _("TLS shutdown failure."));
break;
default:
- /* Socket Error Occured */
+ /* Socket Error Occurred */
openssl_post_errors(M_ERROR, _("TLS shutdown failure."));
break;
}
-
- /* Restore saved flags */
- bsock->restore_blocking(flags);
}
/* Does all the manual labor for tls_bsock_readn() and tls_bsock_writen() */
/* start timer */
bsock->timer_start = watchdog_time;
- bsock->set_timed_out(false);
+ bsock->clear_timed_out();
nleft = nbytes;
break;
case SSL_ERROR_WANT_READ:
+ /* If we timeout on a select, this will be unset */
+ FD_SET((unsigned)bsock->m_fd, &fdset);
+ tv.tv_sec = 10;
+ tv.tv_usec = 0;
+ /* Block until we can read */
+ select(fdmax, &fdset, NULL, NULL, &tv);
+ break;
+
case SSL_ERROR_WANT_WRITE:
/* If we timeout on a select, this will be unset */
FD_SET((unsigned)bsock->m_fd, &fdset);
tv.tv_sec = 10;
tv.tv_usec = 0;
- /* Block until we can read or write */
- select(fdmax, NULL, &fdset, &fdset, &tv);
+ /* Block until we can write */
+ select(fdmax, NULL, &fdset, NULL, &tv);
break;
case SSL_ERROR_ZERO_RETURN: