diff --git a/neon-0.30.2-openssl11.patch b/neon-0.30.2-openssl11.patch new file mode 100644 index 0000000..74c742c --- /dev/null +++ b/neon-0.30.2-openssl11.patch @@ -0,0 +1,234 @@ +--- neon-0.30.2/src/ne_openssl.c.openssl11 ++++ neon-0.30.2/src/ne_openssl.c +@@ -574,6 +574,9 @@ + /* enable workarounds for buggy SSL server implementations */ + SSL_CTX_set_options(ctx->ctx, SSL_OP_ALL); + SSL_CTX_set_verify(ctx->ctx, SSL_VERIFY_PEER, verify_callback); ++#if OPENSSL_VERSION_NUMBER >= 0x10101000L ++ SSL_CTX_set_post_handshake_auth(ctx->ctx, 1); ++#endif + } else if (mode == NE_SSL_CTX_SERVER) { + ctx->ctx = SSL_CTX_new(SSLv23_server_method()); + SSL_CTX_set_session_cache_mode(ctx->ctx, SSL_SESS_CACHE_CLIENT); +@@ -1130,7 +1133,10 @@ + return 0; + } + +-#ifdef NE_HAVE_TS_SSL ++#if defined(NE_HAVE_TS_SSL) && OPENSSL_VERSION_NUMBER < 0x10101000L ++/* For OpenSSL 1.1.1 locking callbacks are no longer need at all. */ ++#define WITH_OPENSSL_LOCKING (1) ++ + /* Implementation of locking callbacks to make OpenSSL thread-safe. + * If the OpenSSL API was better designed, this wouldn't be necessary. + * In OpenSSL releases without CRYPTO_set_idptr_callback, it's not +@@ -1184,8 +1190,6 @@ + } + } + +-#endif +- + /* ID_CALLBACK_IS_{NEON,OTHER} evaluate as true if the currently + * registered OpenSSL ID callback is the neon function (_NEON), or has + * been overwritten by some other app (_OTHER). */ +@@ -1196,6 +1200,8 @@ + #define ID_CALLBACK_IS_OTHER (CRYPTO_get_id_callback() != NULL) + #define ID_CALLBACK_IS_NEON (CRYPTO_get_id_callback() == thread_id_neon) + #endif ++ ++#endif /* NE_HAVE_TS_SSL && OPENSSL_VERSION_NUMBER < 1.1.1 */ + + int ne__ssl_init(void) + { +@@ -1205,7 +1211,7 @@ + SSL_library_init(); + OpenSSL_add_all_algorithms(); + +-#ifdef NE_HAVE_TS_SSL ++#ifdef WITH_OPENSSL_LOCKING + /* If some other library has already come along and set up the + * thread-safety callbacks, then it must be presumed that the + * other library will have a longer lifetime in the process than +@@ -1252,7 +1258,7 @@ + /* Cannot call ERR_free_strings() etc here in case any other code + * in the process using OpenSSL. */ + +-#ifdef NE_HAVE_TS_SSL ++#ifdef WITH_OPENSSL_LOCKING + /* Only unregister the callbacks if some *other* library has not + * come along in the mean-time and trampled over the callbacks + * installed by neon. */ +--- neon-0.30.2/src/ne_pkcs11.c.openssl11 ++++ neon-0.30.2/src/ne_pkcs11.c +@@ -113,13 +113,13 @@ + return 0; + } + +- if (padding != RSA_PKCS1_PADDING) { ++ if (padding != RSA_PKCS1_PADDING && padding != RSA_NO_PADDING) { + NE_DEBUG(NE_DBG_SSL, "pk11: Cannot sign, unknown padding mode '%d'.\n", padding); + RSAerr(PK11_RSA_ERR,ERR_R_RSA_LIB); + return 0; + } + +- mech.mechanism = CKM_RSA_PKCS; ++ mech.mechanism = padding == RSA_PKCS1_PADDING ? CKM_RSA_PKCS : CKM_RSA_X_509; + mech.parameter = NULL; + mech.parameter_len = 0; + +--- neon-0.30.2/src/ne_request.c.openssl11 ++++ neon-0.30.2/src/ne_request.c +@@ -940,6 +940,12 @@ + } + } + ++#ifdef NE_HAVE_SSL ++#define SSL_CC_REQUESTED(_r) (_r->session->ssl_cc_requested) ++#else ++#define SSL_CC_REQUESTED(_r) (0) ++#endif ++ + /* Read and parse response status-line into 'status'. 'retry' is non-zero + * if an NE_RETRY should be returned if an EOF is received. */ + static int read_status_line(ne_request *req, ne_status *status, int retry) +@@ -949,8 +955,11 @@ + + ret = ne_sock_readline(req->session->socket, buffer, sizeof req->respbuf); + if (ret <= 0) { +- int aret = aborted(req, _("Could not read status line"), ret); +- return RETRY_RET(retry, ret, aret); ++ const char *errstr = SSL_CC_REQUESTED(req) ++ ? _("Could not read status line (TLS client certificate was requested)") ++ : _("Could not read status line"); ++ int aret = aborted(req, errstr, ret); ++ return RETRY_RET(retry, ret, aret); + } + + NE_DEBUG(NE_DBG_HTTP, "[status-line] < %s", buffer); +--- neon-0.30.2/src/ne_socket.c.openssl11 ++++ neon-0.30.2/src/ne_socket.c +@@ -179,6 +179,9 @@ + /* Socket read timeout */ + #define SOCKET_READ_TIMEOUT 120 + ++/* Internal read retry value */ ++#define NE_SOCK_RETRY (-6) ++ + /* Critical I/O functions on a socket: useful abstraction for easily + * handling SSL I/O alongside raw socket I/O. */ + struct iofns { +@@ -599,13 +602,50 @@ + + static const struct iofns iofns_raw = { read_raw, write_raw, readable_raw, writev_raw }; + ++static int error_ossl(ne_socket *sock, int sret); ++ + #ifdef HAVE_OPENSSL + /* OpenSSL I/O function implementations. */ + static int readable_ossl(ne_socket *sock, int secs) + { ++#if OPENSSL_VERSION_NUMBER < 0x10101000L ++ /* Sufficient for TLSv1.2 and earlier. */ + if (SSL_pending(sock->ssl)) + return 0; + return readable_raw(sock, secs); ++#else ++ /* TLSv1.3 sends a lot more handshake data so the presence of data ++ * on the socket - i.e. poll() returning 1, is an insufficient ++ * test for app-data readability. */ ++ char pending; ++ int ret; ++ size_t bytes; ++ ++ /* Loop while no app data is pending, each time attempting a one ++ * byte peek, and retrying the poll if that fails due to absence ++ * of app data. */ ++ while (!SSL_pending(sock->ssl)) { ++ ret = readable_raw(sock, secs); ++ if (ret == NE_SOCK_TIMEOUT) { ++ return ret; ++ } ++ ++ ret = SSL_peek_ex(sock->ssl, &pending, 1, &bytes); ++ if (ret) { ++ /* App data definitely available. */ ++ break; ++ } ++ else { ++ /* If this gave SSL_ERROR_WANT_READ, loop and probably ++ * block again, else some other error happened. */ ++ ret = error_ossl(sock, ret); ++ if (ret != NE_SOCK_RETRY) ++ return ret; ++ } ++ } ++ ++ return 0; ++#endif /* OPENSSL_VERSION_NUMBER < 1.1.1 */ + } + + /* SSL error handling, according to SSL_get_error(3). */ +@@ -618,6 +658,10 @@ + set_error(sock, _("Connection closed")); + return NE_SOCK_CLOSED; + } ++ else if (errnum == SSL_ERROR_WANT_READ) { ++ set_error(sock, _("Retry operation")); ++ return NE_SOCK_RETRY; ++ } + + /* for all other errors, look at the OpenSSL error stack */ + err = ERR_get_error(); +@@ -656,13 +700,15 @@ + { + int ret; + +- ret = readable_ossl(sock, sock->rdtimeout); +- if (ret) return ret; +- +- ret = SSL_read(sock->ssl, buffer, CAST2INT(len)); +- if (ret <= 0) +- ret = error_ossl(sock, ret); +- ++ do { ++ ret = readable_ossl(sock, sock->rdtimeout); ++ if (ret) return ret; ++ ++ ret = SSL_read(sock->ssl, buffer, CAST2INT(len)); ++ if (ret <= 0) ++ ret = error_ossl(sock, ret); ++ } while (ret == NE_SOCK_RETRY); ++ + return ret; + } + +@@ -1761,7 +1807,11 @@ + } + + SSL_set_app_data(ssl, userdata); ++#if OPENSSL_VERSION_NUMBER < 0x10101000L + SSL_set_mode(ssl, SSL_MODE_AUTO_RETRY); ++#else ++ SSL_clear_mode(ssl, SSL_MODE_AUTO_RETRY); ++#endif + SSL_set_fd(ssl, sock->fd); + sock->ops = &iofns_ssl; + +@@ -1923,12 +1973,13 @@ + { + int ret; + +- /* Per API description - for an SSL connection, simply send the +- * close_notify but do not wait for the peer's response. */ ++ /* Complete a bidirectional shutdown for SSL/TLS. */ + #if defined(HAVE_OPENSSL) + if (sock->ssl) { +- SSL_shutdown(sock->ssl); +- SSL_free(sock->ssl); ++ if (SSL_shutdown(sock->ssl) == 0) { ++ SSL_shutdown(sock->ssl); ++ } ++ SSL_free(sock->ssl); + } + #elif defined(HAVE_GNUTLS) + if (sock->ssl) { diff --git a/neon.spec b/neon.spec index 22e1c08..e7fef02 100644 --- a/neon.spec +++ b/neon.spec @@ -3,13 +3,14 @@ Summary: An HTTP and WebDAV client library Name: neon Version: 0.30.2 -Release: 9%{?dist} +Release: 10%{?dist} License: LGPLv2+ URL: http://www.webdav.org/neon/ Source0: http://www.webdav.org/neon/neon-%{version}.tar.gz Patch0: neon-0.27.0-multilib.patch Patch1: neon-0.30.2-sysuioh.patch Patch2: neon-0.30.2-lockprintf.patch +Patch3: neon-0.30.2-openssl11.patch BuildRequires: gcc-c++ BuildRequires: expat-devel, openssl-devel, zlib-devel, krb5-devel, libproxy-devel BuildRequires: pkgconfig, pakchois-devel @@ -41,6 +42,7 @@ The development library for the C language HTTP and WebDAV client library. %patch0 -p1 -b .multilib %patch1 -p1 -b .sysuioh %patch2 -p1 -b .lockprintf +%patch3 -p1 -b .openssl11 # prevent installation of HTML docs sed -ibak '/^install-docs/s/install-html//' Makefile.in @@ -84,6 +86,9 @@ make %{?_smp_mflags} check %{_libdir}/*.so %changelog +* Fri Apr 5 2019 Joe Orton - 0.30.2-10 +- updates for OpenSSL 1.1 (#1675444) + * Fri Feb 01 2019 Fedora Release Engineering - 0.30.2-9 - Rebuilt for https://fedoraproject.org/wiki/Fedora_30_Mass_Rebuild