summaryrefslogtreecommitdiffstats
path: root/Utilities
diff options
context:
space:
mode:
authorBrad King <brad.king@kitware.com>2023-10-12 19:29:04 (GMT)
committerBrad King <brad.king@kitware.com>2023-10-12 19:29:20 (GMT)
commitdf4efb72e4225dc3fd4f32313bc8b19122a98f66 (patch)
treedbbb93a136f4f44184cbab061b03489379ef717c /Utilities
parent8f6a6b02e59c112dbe971adca4f25938903828ea (diff)
parente6a6c1abc1e6b6e3ca9fa77947279509b55e2b01 (diff)
downloadCMake-df4efb72e4225dc3fd4f32313bc8b19122a98f66.zip
CMake-df4efb72e4225dc3fd4f32313bc8b19122a98f66.tar.gz
CMake-df4efb72e4225dc3fd4f32313bc8b19122a98f66.tar.bz2
Merge branch 'upstream-curl' into update-curl
* upstream-curl: curl 2023-10-11 (d755a5f7) Issue: #25329
Diffstat (limited to 'Utilities')
-rw-r--r--Utilities/cmcurl/CMake/CurlSymbolHiding.cmake6
-rw-r--r--Utilities/cmcurl/CMake/CurlTests.c17
-rw-r--r--Utilities/cmcurl/CMake/FindNGTCP2.cmake6
-rw-r--r--Utilities/cmcurl/CMake/OtherTests.cmake92
-rw-r--r--Utilities/cmcurl/CMake/Platforms/WindowsCache.cmake20
-rw-r--r--Utilities/cmcurl/CMakeLists.txt266
-rw-r--r--Utilities/cmcurl/include/curl/curl.h10
-rw-r--r--Utilities/cmcurl/include/curl/curlver.h6
-rw-r--r--Utilities/cmcurl/include/curl/multi.h11
-rw-r--r--Utilities/cmcurl/lib/CMakeLists.txt51
-rw-r--r--Utilities/cmcurl/lib/Makefile.inc6
-rw-r--r--Utilities/cmcurl/lib/base64.c2
-rw-r--r--Utilities/cmcurl/lib/bufq.c22
-rw-r--r--Utilities/cmcurl/lib/bufq.h6
-rw-r--r--Utilities/cmcurl/lib/c-hyper.c16
-rw-r--r--Utilities/cmcurl/lib/cf-h1-proxy.c289
-rw-r--r--Utilities/cmcurl/lib/cf-h2-proxy.c79
-rw-r--r--Utilities/cmcurl/lib/cf-socket.c35
-rw-r--r--Utilities/cmcurl/lib/conncache.c1
-rw-r--r--Utilities/cmcurl/lib/connect.c8
-rw-r--r--Utilities/cmcurl/lib/content_encoding.c151
-rw-r--r--Utilities/cmcurl/lib/content_encoding.h22
-rw-r--r--Utilities/cmcurl/lib/cookie.c132
-rw-r--r--Utilities/cmcurl/lib/cookie.h18
-rw-r--r--Utilities/cmcurl/lib/curl_config.h.cmake74
-rw-r--r--Utilities/cmcurl/lib/curl_ctype.h4
-rw-r--r--Utilities/cmcurl/lib/curl_hmac.h4
-rw-r--r--Utilities/cmcurl/lib/curl_memrchr.h4
-rw-r--r--Utilities/cmcurl/lib/curl_ntlm_wb.c2
-rw-r--r--Utilities/cmcurl/lib/curl_setup.h8
-rw-r--r--Utilities/cmcurl/lib/curl_sspi.h245
-rw-r--r--Utilities/cmcurl/lib/curl_threads.c2
-rw-r--r--Utilities/cmcurl/lib/curl_threads.h3
-rw-r--r--Utilities/cmcurl/lib/curl_trc.c4
-rw-r--r--Utilities/cmcurl/lib/doh.c5
-rw-r--r--Utilities/cmcurl/lib/dynbuf.h1
-rw-r--r--Utilities/cmcurl/lib/dynhds.c3
-rw-r--r--Utilities/cmcurl/lib/easy.c46
-rw-r--r--Utilities/cmcurl/lib/easy_lock.h7
-rw-r--r--Utilities/cmcurl/lib/escape.c55
-rw-r--r--Utilities/cmcurl/lib/escape.h5
-rw-r--r--Utilities/cmcurl/lib/file.c4
-rw-r--r--Utilities/cmcurl/lib/fopen.c2
-rw-r--r--Utilities/cmcurl/lib/formdata.c17
-rw-r--r--Utilities/cmcurl/lib/ftp.c35
-rw-r--r--Utilities/cmcurl/lib/ftplistparser.c2
-rw-r--r--Utilities/cmcurl/lib/hmac.c4
-rw-r--r--Utilities/cmcurl/lib/hostip.c4
-rw-r--r--Utilities/cmcurl/lib/hostip.h2
-rw-r--r--Utilities/cmcurl/lib/http.c24
-rw-r--r--Utilities/cmcurl/lib/http1.c24
-rw-r--r--Utilities/cmcurl/lib/http1.h2
-rw-r--r--Utilities/cmcurl/lib/http2.c6
-rw-r--r--Utilities/cmcurl/lib/http_aws_sigv4.c13
-rw-r--r--Utilities/cmcurl/lib/http_chunks.c5
-rw-r--r--Utilities/cmcurl/lib/http_proxy.c108
-rw-r--r--Utilities/cmcurl/lib/http_proxy.h9
-rw-r--r--Utilities/cmcurl/lib/idn.c5
-rw-r--r--Utilities/cmcurl/lib/inet_ntop.c10
-rw-r--r--Utilities/cmcurl/lib/ldap.c4
-rw-r--r--Utilities/cmcurl/lib/mime.c6
-rw-r--r--Utilities/cmcurl/lib/mime.h2
-rw-r--r--Utilities/cmcurl/lib/mqtt.c108
-rw-r--r--Utilities/cmcurl/lib/mqtt.h1
-rw-r--r--Utilities/cmcurl/lib/multi.c85
-rw-r--r--Utilities/cmcurl/lib/multiif.h9
-rw-r--r--Utilities/cmcurl/lib/openldap.c21
-rw-r--r--Utilities/cmcurl/lib/pingpong.c2
-rw-r--r--Utilities/cmcurl/lib/progress.c9
-rw-r--r--Utilities/cmcurl/lib/progress.h5
-rw-r--r--Utilities/cmcurl/lib/rand.c48
-rw-r--r--Utilities/cmcurl/lib/rand.h7
-rw-r--r--Utilities/cmcurl/lib/sendf.c205
-rw-r--r--Utilities/cmcurl/lib/sendf.h65
-rw-r--r--Utilities/cmcurl/lib/setopt.c2
-rw-r--r--Utilities/cmcurl/lib/sigpipe.h2
-rw-r--r--Utilities/cmcurl/lib/smb.c7
-rw-r--r--Utilities/cmcurl/lib/socks.c8
-rw-r--r--Utilities/cmcurl/lib/telnet.c5
-rw-r--r--Utilities/cmcurl/lib/tftp.c7
-rw-r--r--Utilities/cmcurl/lib/timeval.c14
-rw-r--r--Utilities/cmcurl/lib/timeval.h18
-rw-r--r--Utilities/cmcurl/lib/transfer.c45
-rw-r--r--Utilities/cmcurl/lib/url.c55
-rw-r--r--Utilities/cmcurl/lib/urlapi.c12
-rw-r--r--Utilities/cmcurl/lib/urldata.h11
-rw-r--r--Utilities/cmcurl/lib/vauth/cleartext.c1
-rw-r--r--Utilities/cmcurl/lib/vquic/curl_ngtcp2.c53
-rw-r--r--Utilities/cmcurl/lib/vquic/curl_quiche.c13
-rw-r--r--Utilities/cmcurl/lib/vssh/libssh.c10
-rw-r--r--Utilities/cmcurl/lib/vssh/libssh2.c16
-rw-r--r--Utilities/cmcurl/lib/vssh/wolfssh.c1
-rw-r--r--Utilities/cmcurl/lib/vtls/gtls.c8
-rw-r--r--Utilities/cmcurl/lib/vtls/mbedtls.c13
-rw-r--r--Utilities/cmcurl/lib/vtls/openssl.c100
-rw-r--r--Utilities/cmcurl/lib/vtls/schannel.c48
-rw-r--r--Utilities/cmcurl/lib/vtls/schannel.h2
-rw-r--r--Utilities/cmcurl/lib/vtls/schannel_int.h43
-rw-r--r--Utilities/cmcurl/lib/vtls/sectransp.c16
-rw-r--r--Utilities/cmcurl/lib/vtls/vtls.c3
-rw-r--r--Utilities/cmcurl/lib/vtls/wolfssl.c71
-rw-r--r--Utilities/cmcurl/lib/warnless.c51
102 files changed, 1646 insertions, 1586 deletions
diff --git a/Utilities/cmcurl/CMake/CurlSymbolHiding.cmake b/Utilities/cmcurl/CMake/CurlSymbolHiding.cmake
index 142e919..8289b49 100644
--- a/Utilities/cmcurl/CMake/CurlSymbolHiding.cmake
+++ b/Utilities/cmcurl/CMake/CurlSymbolHiding.cmake
@@ -26,6 +26,12 @@ include(CheckCSourceCompiles)
option(CURL_HIDDEN_SYMBOLS "Set to ON to hide libcurl internal symbols (=hide all symbols that aren't officially external)." ON)
mark_as_advanced(CURL_HIDDEN_SYMBOLS)
+if(WIN32 AND ENABLE_CURLDEBUG)
+ # We need to export internal debug functions (e.g. curl_dbg_*), so disable
+ # symbol hiding for debug builds.
+ set(CURL_HIDDEN_SYMBOLS OFF)
+endif()
+
if(CURL_HIDDEN_SYMBOLS)
set(SUPPORTS_SYMBOL_HIDING FALSE)
diff --git a/Utilities/cmcurl/CMake/CurlTests.c b/Utilities/cmcurl/CMake/CurlTests.c
index 38be522..ea80ec8 100644
--- a/Utilities/cmcurl/CMake/CurlTests.c
+++ b/Utilities/cmcurl/CMake/CurlTests.c
@@ -21,23 +21,6 @@
* SPDX-License-Identifier: curl
*
***************************************************************************/
-#ifdef TIME_WITH_SYS_TIME
-/* Time with sys/time test */
-
-#include <sys/types.h>
-#include <sys/time.h>
-#include <time.h>
-
-int
-main ()
-{
-if ((struct tm *) 0)
-return 0;
- ;
- return 0;
-}
-
-#endif
#ifdef HAVE_FCNTL_O_NONBLOCK
diff --git a/Utilities/cmcurl/CMake/FindNGTCP2.cmake b/Utilities/cmcurl/CMake/FindNGTCP2.cmake
index ae92e41..7ea4665 100644
--- a/Utilities/cmcurl/CMake/FindNGTCP2.cmake
+++ b/Utilities/cmcurl/CMake/FindNGTCP2.cmake
@@ -31,8 +31,10 @@ Find the ngtcp2 library
This module accepts optional COMPONENTS to control the crypto library (these are
mutually exclusive)::
- OpenSSL: Use libngtcp2_crypto_quictls
- GnuTLS: Use libngtcp2_crypto_gnutls
+ quictls, LibreSSL: Use libngtcp2_crypto_quictls
+ BoringSSL, AWS-LC: Use libngtcp2_crypto_boringssl
+ wolfSSL: Use libngtcp2_crypto_wolfssl
+ GnuTLS: Use libngtcp2_crypto_gnutls
Result Variables
^^^^^^^^^^^^^^^^
diff --git a/Utilities/cmcurl/CMake/OtherTests.cmake b/Utilities/cmcurl/CMake/OtherTests.cmake
index 762e6d1..d67a905 100644
--- a/Utilities/cmcurl/CMake/OtherTests.cmake
+++ b/Utilities/cmcurl/CMake/OtherTests.cmake
@@ -22,6 +22,8 @@
#
###########################################################################
include(CheckCSourceCompiles)
+include(CheckCSourceRuns)
+
# The begin of the sources (macros and includes)
set(_source_epilogue "#undef inline")
@@ -57,10 +59,9 @@ check_c_source_compiles("${_source_epilogue}
if(NOT HAVE_WINDOWS_H)
add_header_include(HAVE_SYS_TIME_H "sys/time.h")
- add_header_include(TIME_WITH_SYS_TIME "time.h")
- add_header_include(HAVE_TIME_H "time.h")
endif()
check_c_source_compiles("${_source_epilogue}
+#include <time.h>
int main(void) {
struct timeval ts;
ts.tv_sec = 0;
@@ -90,7 +91,6 @@ if(NOT CMAKE_CROSSCOMPILING)
# only try this on non-apple platforms
# if not cross-compilation...
- include(CheckCSourceRuns)
set(CMAKE_REQUIRED_FLAGS "")
if(HAVE_SYS_POLL_H)
set(CMAKE_REQUIRED_FLAGS "-DHAVE_SYS_POLL_H")
@@ -133,3 +133,89 @@ if(NOT CMAKE_CROSSCOMPILING)
}" HAVE_POLL_FINE)
endif()
endif()
+
+# Detect HAVE_GETADDRINFO_THREADSAFE
+
+if(WIN32)
+ set(HAVE_GETADDRINFO_THREADSAFE ${HAVE_GETADDRINFO})
+elseif(NOT HAVE_GETADDRINFO)
+ set(HAVE_GETADDRINFO_THREADSAFE FALSE)
+elseif(CMAKE_SYSTEM_NAME STREQUAL "AIX" OR
+ CMAKE_SYSTEM_NAME STREQUAL "Darwin" OR
+ CMAKE_SYSTEM_NAME STREQUAL "FreeBSD" OR
+ CMAKE_SYSTEM_NAME STREQUAL "HP-UX" OR
+ CMAKE_SYSTEM_NAME STREQUAL "MidnightBSD" OR
+ CMAKE_SYSTEM_NAME STREQUAL "NetBSD" OR
+ CMAKE_SYSTEM_NAME STREQUAL "SunOS")
+ set(HAVE_GETADDRINFO_THREADSAFE TRUE)
+elseif(CMAKE_SYSTEM_NAME MATCHES "BSD")
+ set(HAVE_GETADDRINFO_THREADSAFE FALSE)
+endif()
+
+if(NOT DEFINED HAVE_GETADDRINFO_THREADSAFE)
+
+ set(_save_epilogue "${_source_epilogue}")
+ set(_source_epilogue "#undef inline")
+
+ add_header_include(HAVE_SYS_SOCKET_H "sys/socket.h")
+ add_header_include(HAVE_SYS_TIME_H "sys/time.h")
+ add_header_include(HAVE_NETDB_H "netdb.h")
+
+ check_c_source_compiles("${_source_epilogue}
+ int main(void)
+ {
+ #ifdef h_errno
+ return 0;
+ #else
+ force compilation error
+ #endif
+ }" HAVE_H_ERRNO)
+
+ if(NOT HAVE_H_ERRNO)
+ check_c_source_runs("${_source_epilogue}
+ int main(void)
+ {
+ h_errno = 2;
+ return h_errno != 0 ? 1 : 0;
+ }" HAVE_H_ERRNO_ASSIGNABLE)
+
+ if(NOT HAVE_H_ERRNO_ASSIGNABLE)
+ check_c_source_compiles("${_source_epilogue}
+ int main(void)
+ {
+ #if defined(_POSIX_C_SOURCE) && (_POSIX_C_SOURCE >= 200809L)
+ return 0;
+ #elif defined(_XOPEN_SOURCE) && (_XOPEN_SOURCE >= 700)
+ return 0;
+ #else
+ force compilation error
+ #endif
+ }" HAVE_H_ERRNO_SBS_ISSUE_7)
+ endif()
+ endif()
+
+ if(HAVE_H_ERRNO OR HAVE_H_ERRNO_ASSIGNABLE OR HAVE_H_ERRNO_SBS_ISSUE_7)
+ set(HAVE_GETADDRINFO_THREADSAFE TRUE)
+ endif()
+
+ set(_source_epilogue "${_save_epilogue}")
+endif()
+
+if(NOT DEFINED HAVE_CLOCK_GETTIME_MONOTONIC_RAW)
+ set(_save_epilogue "${_source_epilogue}")
+ set(_source_epilogue "#undef inline")
+
+ add_header_include(HAVE_SYS_TYPES_H "sys/types.h")
+ add_header_include(HAVE_SYS_TIME_H "sys/time.h")
+
+ check_c_source_compiles("${_source_epilogue}
+ #include <time.h>
+ int main(void)
+ {
+ struct timespec ts;
+ (void)clock_gettime(CLOCK_MONOTONIC_RAW, &ts);
+ return 0;
+ }" HAVE_CLOCK_GETTIME_MONOTONIC_RAW)
+
+ set(_source_epilogue "${_save_epilogue}")
+endif()
diff --git a/Utilities/cmcurl/CMake/Platforms/WindowsCache.cmake b/Utilities/cmcurl/CMake/Platforms/WindowsCache.cmake
index 44a1fc9..5daec0e 100644
--- a/Utilities/cmcurl/CMake/Platforms/WindowsCache.cmake
+++ b/Utilities/cmcurl/CMake/Platforms/WindowsCache.cmake
@@ -33,6 +33,7 @@ if(NOT UNIX)
set(HAVE_UNISTD_H 1)
set(HAVE_INTTYPES_H 1)
set(HAVE_STRTOLL 1)
+ set(HAVE_BASENAME 1)
elseif(MSVC)
if(NOT MSVC_VERSION LESS 1800)
set(HAVE_INTTYPES_H 1)
@@ -46,30 +47,32 @@ if(NOT UNIX)
else()
set(HAVE_SNPRINTF 0)
endif()
+ set(HAVE_BASENAME 0)
endif()
set(HAVE_LIBSOCKET 0)
set(HAVE_GETHOSTNAME 1)
set(HAVE_LIBZ 0)
+ set(HAVE_ARC4RANDOM 0)
+ set(HAVE_FNMATCH 0)
+ set(HAVE_SCHED_YIELD 0)
set(HAVE_ARPA_INET_H 0)
- set(HAVE_ARPA_TFTP_H 0)
set(HAVE_FCNTL_H 1)
set(HAVE_IFADDRS_H 0)
set(HAVE_IO_H 1)
set(HAVE_NETDB_H 0)
set(HAVE_NETINET_IN_H 0)
set(HAVE_NETINET_TCP_H 0)
+ set(HAVE_NETINET_UDP_H 0)
set(HAVE_NET_IF_H 0)
set(HAVE_IOCTL_SIOCGIFADDR 0)
set(HAVE_POLL_H 0)
+ set(HAVE_POLL_FINE 0)
set(HAVE_PWD_H 0)
- set(HAVE_SETJMP_H 1)
- set(HAVE_SIGNAL_H 1)
- set(HAVE_STDLIB_H 1)
set(HAVE_STRINGS_H 0)
- set(HAVE_STRING_H 1)
set(HAVE_SYS_FILIO_H 0)
+ set(HAVE_SYS_WAIT_H 0)
set(HAVE_SYS_IOCTL_H 0)
set(HAVE_SYS_PARAM_H 0)
set(HAVE_SYS_POLL_H 0)
@@ -84,14 +87,16 @@ if(NOT UNIX)
set(HAVE_SYS_UTIME_H 1)
set(HAVE_TERMIOS_H 0)
set(HAVE_TERMIO_H 0)
- set(HAVE_TIME_H 1)
set(HAVE_UTIME_H 0)
+ set(HAVE_FSEEKO 0)
+ set(HAVE__FSEEKI64 1)
set(HAVE_SOCKET 1)
set(HAVE_SELECT 1)
set(HAVE_STRDUP 1)
set(HAVE_STRICMP 1)
set(HAVE_STRCMPI 1)
+ set(HAVE_MEMRCHR 0)
set(HAVE_GETTIMEOFDAY 0)
set(HAVE_CLOSESOCKET 1)
set(HAVE_SIGSETJMP 0)
@@ -101,11 +106,13 @@ if(NOT UNIX)
set(HAVE_GETEUID 0)
set(HAVE_UTIME 1)
set(HAVE_GMTIME_R 0)
+ set(HAVE_CLOCK_GETTIME_MONOTONIC_RAW 0)
set(HAVE_GETHOSTBYNAME_R 0)
set(HAVE_SIGNAL 1)
set(HAVE_LINUX_TCP_H 0)
set(HAVE_GLIBC_STRERROR_R 0)
set(HAVE_MACH_ABSOLUTE_TIME 0)
+ set(HAVE_GETIFADDRS 0)
set(HAVE_GETHOSTBYNAME_R_3 0)
set(HAVE_GETHOSTBYNAME_R_3_REENTRANT 0)
@@ -114,7 +121,6 @@ if(NOT UNIX)
set(HAVE_GETHOSTBYNAME_R_6 0)
set(HAVE_GETHOSTBYNAME_R_6_REENTRANT 0)
- set(TIME_WITH_SYS_TIME 0)
set(HAVE_O_NONBLOCK 0)
set(HAVE_IN_ADDR_T 0)
set(STDC_HEADERS 1)
diff --git a/Utilities/cmcurl/CMakeLists.txt b/Utilities/cmcurl/CMakeLists.txt
index c30a1d8..04efc50 100644
--- a/Utilities/cmcurl/CMakeLists.txt
+++ b/Utilities/cmcurl/CMakeLists.txt
@@ -203,9 +203,9 @@ endif()
# https://cmake.org/cmake/help/latest/module/FetchContent.html#integrating-with-find-package
#
# The following variables are available:
-# HAVE_SSL_SET0_WBIO: `SSL_set0_wbio` present in OpenSSL
-# HAVE_AWSLC: OpenSSL is AWS-LC
-# HAVE_BORINGSSL: OpenSSL is BoringSSL
+# HAVE_SSL_SET0_WBIO: `SSL_set0_wbio` present in OpenSSL/wolfSSL
+# HAVE_OPENSSL_SRP: `SSL_CTX_set_srp_username` present in OpenSSL/wolfSSL
+# HAVE_GNUTLS_SRP: `gnutls_srp_verifier` present in GnuTLS
# HAVE_SSL_CTX_SET_QUIC_METHOD: `SSL_CTX_set_quic_method` present in OpenSSL/wolfSSL
# HAVE_QUICHE_CONN_SET_QLOG_FD: `quiche_conn_set_qlog_fd` present in QUICHE
# HAVE_ZSTD_CREATEDSTREAM: `ZSTD_createDStream` present in Zstd
@@ -256,7 +256,7 @@ option(CURL_WERROR "Turn compiler warnings into errors" OFF)
option(PICKY_COMPILER "Enable picky compiler options" ON)
option(BUILD_CURL_EXE "Set to ON to build curl executable." ON)
option(BUILD_SHARED_LIBS "Build shared libraries" ON)
-option(BUILD_STATIC_LIBS "Build shared libraries" OFF)
+option(BUILD_STATIC_LIBS "Build static libraries" OFF)
option(BUILD_STATIC_CURL "Build curl executable with static libcurl" OFF)
option(ENABLE_ARES "Set to ON to enable c-ares support" OFF)
if(WIN32)
@@ -351,6 +351,8 @@ mark_as_advanced(CURL_ENABLE_EXPORT_TARGET)
option(CURL_DISABLE_ALTSVC "disables alt-svc support" OFF)
mark_as_advanced(CURL_DISABLE_ALTSVC)
+option(CURL_DISABLE_SRP "disables TLS-SRP support" OFF)
+mark_as_advanced(CURL_DISABLE_SRP)
option(CURL_DISABLE_COOKIES "disables cookies support" OFF)
mark_as_advanced(CURL_DISABLE_COOKIES)
option(CURL_DISABLE_BASIC_AUTH "disables Basic authentication" OFF)
@@ -466,7 +468,7 @@ if(ENABLE_IPV6 AND NOT WIN32)
endif()
if(CMAKE_SYSTEM_NAME STREQUAL "Darwin" AND NOT ENABLE_ARES)
- set(use_core_foundation ON)
+ set(use_core_foundation_and_core_services ON)
find_library(SYSTEMCONFIGURATION_FRAMEWORK "SystemConfiguration")
if(NOT SYSTEMCONFIGURATION_FRAMEWORK)
@@ -551,25 +553,16 @@ if(WIN32)
if(USE_LIBRTMP)
list(APPEND CURL_LIBS "winmm")
endif()
-
- # Matching logic used for Curl_win32_random()
- if(MINGW)
- check_c_source_compiles("
- #include <_mingw.h>
- #if defined(__MINGW64_VERSION_MAJOR)
- #error
- #endif
- int main(void) {
- return 0;
- }"
- HAVE_MINGW_ORIGINAL)
- endif()
endif()
if(0) # This code not needed for building within CMake.
# check SSL libraries
option(CURL_ENABLE_SSL "Enable SSL support" ON)
+if(CURL_DEFAULT_SSL_BACKEND)
+ set(valid_default_ssl_backend FALSE)
+endif()
+
if(APPLE)
cmake_dependent_option(CURL_USE_SECTRANSP "Enable Apple OS native SSL/TLS" OFF CURL_ENABLE_SSL OFF)
endif()
@@ -581,7 +574,7 @@ endif()
cmake_dependent_option(CURL_USE_MBEDTLS "Enable mbedTLS for SSL/TLS" OFF CURL_ENABLE_SSL OFF)
cmake_dependent_option(CURL_USE_BEARSSL "Enable BearSSL for SSL/TLS" OFF CURL_ENABLE_SSL OFF)
cmake_dependent_option(CURL_USE_WOLFSSL "Enable wolfSSL for SSL/TLS" OFF CURL_ENABLE_SSL OFF)
-cmake_dependent_option(CURL_USE_GNUTLS "Enable GNUTLS for SSL/TLS" OFF CURL_ENABLE_SSL OFF)
+cmake_dependent_option(CURL_USE_GNUTLS "Enable GnuTLS for SSL/TLS" OFF CURL_ENABLE_SSL OFF)
set(openssl_default ON)
if(WIN32 OR CURL_USE_SECTRANSP OR CURL_USE_SCHANNEL OR CURL_USE_MBEDTLS OR CURL_USE_WOLFSSL)
@@ -607,13 +600,17 @@ if(CURL_USE_SCHANNEL)
set(SSL_ENABLED ON)
set(USE_SCHANNEL ON) # Windows native SSL/TLS support
set(USE_WINDOWS_SSPI ON) # CURL_USE_SCHANNEL implies CURL_WINDOWS_SSPI
+
+ if(CURL_DEFAULT_SSL_BACKEND AND CURL_DEFAULT_SSL_BACKEND STREQUAL "schannel")
+ set(valid_default_ssl_backend TRUE)
+ endif()
endif()
if(CURL_WINDOWS_SSPI)
set(USE_WINDOWS_SSPI ON)
endif()
if(CURL_USE_SECTRANSP)
- set(use_core_foundation ON)
+ set(use_core_foundation_and_core_services ON)
find_library(SECURITY_FRAMEWORK "Security")
if(NOT SECURITY_FRAMEWORK)
@@ -623,15 +620,24 @@ if(CURL_USE_SECTRANSP)
set(SSL_ENABLED ON)
set(USE_SECTRANSP ON)
list(APPEND CURL_LIBS "-framework Security")
+
+ if(CURL_DEFAULT_SSL_BACKEND AND CURL_DEFAULT_SSL_BACKEND STREQUAL "secure-transport")
+ set(valid_default_ssl_backend TRUE)
+ endif()
endif()
-if(use_core_foundation)
+if(use_core_foundation_and_core_services)
find_library(COREFOUNDATION_FRAMEWORK "CoreFoundation")
+ find_library(CORESERVICES_FRAMEWORK "CoreServices")
+
if(NOT COREFOUNDATION_FRAMEWORK)
message(FATAL_ERROR "CoreFoundation framework not found")
endif()
+ if(NOT CORESERVICES_FRAMEWORK)
+ message(FATAL_ERROR "CoreServices framework not found")
+ endif()
- list(APPEND CURL_LIBS "-framework CoreFoundation")
+ list(APPEND CURL_LIBS "-framework CoreFoundation -framework CoreServices")
endif()
if(CURL_USE_OPENSSL)
@@ -648,9 +654,11 @@ if(CURL_USE_OPENSSL)
if(WIN32)
list(APPEND CURL_LIBS "ws2_32")
- if(NOT HAVE_MINGW_ORIGINAL)
- list(APPEND CURL_LIBS "bcrypt") # for OpenSSL/LibreSSL
- endif()
+ list(APPEND CURL_LIBS "bcrypt") # for OpenSSL/LibreSSL
+ endif()
+
+ if(CURL_DEFAULT_SSL_BACKEND AND CURL_DEFAULT_SSL_BACKEND STREQUAL "openssl")
+ set(valid_default_ssl_backend TRUE)
endif()
set(CMAKE_REQUIRED_INCLUDES ${OPENSSL_INCLUDE_DIR})
@@ -677,6 +685,10 @@ if(CURL_USE_MBEDTLS)
set(USE_MBEDTLS ON)
list(APPEND CURL_LIBS ${MBEDTLS_LIBRARIES})
include_directories(${MBEDTLS_INCLUDE_DIRS})
+
+ if(CURL_DEFAULT_SSL_BACKEND AND CURL_DEFAULT_SSL_BACKEND STREQUAL "mbedtls")
+ set(valid_default_ssl_backend TRUE)
+ endif()
endif()
if(CURL_USE_BEARSSL)
@@ -685,6 +697,10 @@ if(CURL_USE_BEARSSL)
set(USE_BEARSSL ON)
list(APPEND CURL_LIBS ${BEARSSL_LIBRARY})
include_directories(${BEARSSL_INCLUDE_DIRS})
+
+ if(CURL_DEFAULT_SSL_BACKEND AND CURL_DEFAULT_SSL_BACKEND STREQUAL "bearssl")
+ set(valid_default_ssl_backend TRUE)
+ endif()
endif()
if(CURL_USE_WOLFSSL)
@@ -693,11 +709,34 @@ if(CURL_USE_WOLFSSL)
set(USE_WOLFSSL ON)
list(APPEND CURL_LIBS ${WolfSSL_LIBRARIES})
include_directories(${WolfSSL_INCLUDE_DIRS})
+
+ if(CURL_DEFAULT_SSL_BACKEND AND CURL_DEFAULT_SSL_BACKEND STREQUAL "wolfssl")
+ set(valid_default_ssl_backend TRUE)
+ endif()
endif()
if(CURL_USE_GNUTLS)
- set(SSL_ENABLED ON)
- set(USE_GNUTLS ON)
+ find_package(GnuTLS REQUIRED)
+ set(SSL_ENABLED ON)
+ set(USE_GNUTLS ON)
+ list(APPEND CURL_LIBS ${GNUTLS_LIBRARIES} "nettle")
+ include_directories(${GNUTLS_INCLUDE_DIRS})
+
+ if(CURL_DEFAULT_SSL_BACKEND AND CURL_DEFAULT_SSL_BACKEND STREQUAL "gnutls")
+ set(valid_default_ssl_backend TRUE)
+ endif()
+
+ if(NOT DEFINED HAVE_GNUTLS_SRP AND NOT CURL_DISABLE_SRP)
+ cmake_push_check_state()
+ set(CMAKE_REQUIRED_INCLUDES ${GNUTLS_INCLUDE_DIRS})
+ set(CMAKE_REQUIRED_LIBRARIES ${GNUTLS_LIBRARIES})
+ check_symbol_exists(gnutls_srp_verifier "gnutls/gnutls.h" HAVE_GNUTLS_SRP)
+ cmake_pop_check_state()
+ endif()
+endif()
+
+if(CURL_DEFAULT_SSL_BACKEND AND NOT valid_default_ssl_backend)
+ message(FATAL_ERROR "CURL_DEFAULT_SSL_BACKEND '${CURL_DEFAULT_SSL_BACKEND}' not enabled.")
endif()
# Keep ZLIB detection after TLS detection,
@@ -743,7 +782,7 @@ option(CURL_ZSTD "Set to ON to enable building curl with zstd support." OFF)
set(HAVE_ZSTD OFF)
if(CURL_ZSTD)
find_package(Zstd REQUIRED)
- if (NOT DEFINED HAVE_ZSTD_CREATEDSTREAM)
+ if(NOT DEFINED HAVE_ZSTD_CREATEDSTREAM)
cmake_push_check_state()
set(CMAKE_REQUIRED_INCLUDES ${Zstd_INCLUDE_DIRS})
set(CMAKE_REQUIRED_LIBRARIES ${Zstd_LIBRARIES})
@@ -768,9 +807,7 @@ macro(openssl_check_symbol_exists SYMBOL FILES VARIABLE)
endif()
if(WIN32)
list(APPEND CMAKE_REQUIRED_LIBRARIES "ws2_32")
- if(NOT HAVE_MINGW_ORIGINAL)
- list(APPEND CMAKE_REQUIRED_LIBRARIES "bcrypt") # for OpenSSL/LibreSSL
- endif()
+ list(APPEND CMAKE_REQUIRED_LIBRARIES "bcrypt") # for OpenSSL/LibreSSL
endif()
elseif(USE_WOLFSSL)
set(CMAKE_REQUIRED_INCLUDES "${WolfSSL_INCLUDE_DIRS}")
@@ -792,6 +829,9 @@ if(USE_OPENSSL OR USE_WOLFSSL)
if(NOT DEFINED HAVE_SSL_SET0_WBIO)
openssl_check_symbol_exists(SSL_set0_wbio "openssl/ssl.h" HAVE_SSL_SET0_WBIO)
endif()
+ if(NOT DEFINED HAVE_OPENSSL_SRP AND NOT CURL_DISABLE_SRP)
+ openssl_check_symbol_exists(SSL_CTX_set_srp_username "openssl/ssl.h" HAVE_OPENSSL_SRP)
+ endif()
endif()
option(USE_NGHTTP2 "Use nghttp2 library" OFF)
@@ -806,7 +846,7 @@ if(USE_NGTCP2)
if(USE_OPENSSL OR USE_WOLFSSL)
if(USE_WOLFSSL)
find_package(NGTCP2 REQUIRED wolfSSL)
- elseif(HAVE_BORINGSSL)
+ elseif(HAVE_BORINGSSL OR HAVE_AWSLC)
find_package(NGTCP2 REQUIRED BoringSSL)
else()
find_package(NGTCP2 REQUIRED quictls)
@@ -823,9 +863,7 @@ if(USE_NGTCP2)
if(NOT HAVE_SSL_CTX_SET_QUIC_METHOD)
message(FATAL_ERROR "QUIC support is missing in OpenSSL/LibreSSL/BoringSSL/wolfSSL. Try setting -DOPENSSL_ROOT_DIR")
endif()
-
elseif(USE_GNUTLS)
- # TODO add GnuTLS support as vtls library.
find_package(NGTCP2 REQUIRED GnuTLS)
else()
message(FATAL_ERROR "ngtcp2 requires OpenSSL, wolfSSL or GnuTLS")
@@ -869,6 +907,10 @@ if(USE_MSH3)
list(APPEND CURL_LIBS ${MSH3_LIBRARIES})
endif()
+if(NOT CURL_DISABLE_SRP AND (HAVE_GNUTLS_SRP OR HAVE_OPENSSL_SRP))
+ set(USE_TLS_SRP 1)
+endif()
+
if(NOT CURL_DISABLE_LDAP)
if(WIN32)
option(USE_WIN32_LDAP "Use Windows LDAP implementation" ON)
@@ -880,15 +922,9 @@ if(NOT CURL_DISABLE_LDAP)
endif()
endif()
- option(CURL_USE_OPENLDAP "Use OpenLDAP code." OFF)
- mark_as_advanced(CURL_USE_OPENLDAP)
set(CMAKE_LDAP_LIB "ldap" CACHE STRING "Name or full path to ldap library")
set(CMAKE_LBER_LIB "lber" CACHE STRING "Name or full path to lber library")
- if(CURL_USE_OPENLDAP AND USE_WIN32_LDAP)
- message(FATAL_ERROR "Cannot use USE_WIN32_LDAP and CURL_USE_OPENLDAP at the same time")
- endif()
-
# Now that we know, we're not using windows LDAP...
if(NOT USE_WIN32_LDAP)
# Check for LDAP
@@ -913,9 +949,6 @@ if(NOT CURL_DISABLE_LDAP)
set(CURL_DISABLE_LDAP ON CACHE BOOL "" FORCE)
set(CMAKE_REQUIRED_INCLUDES ${CMAKE_REQUIRED_INCLUDES_BAK}) #LDAP includes won't be used
else()
- if(CURL_USE_OPENLDAP)
- set(USE_OPENLDAP ON)
- endif()
if(CMAKE_LDAP_INCLUDE_DIR)
include_directories(${CMAKE_LDAP_INCLUDE_DIR})
endif()
@@ -929,13 +962,18 @@ if(NOT CURL_DISABLE_LDAP)
endif()
list(APPEND _HEADER_LIST "ldap.h")
- set(_SRC_STRING "")
+ set(_INCLUDE_STRING "")
foreach(_HEADER ${_HEADER_LIST})
set(_INCLUDE_STRING "${_INCLUDE_STRING}#include <${_HEADER}>\n")
endforeach()
- set(_SRC_STRING
- "
+ list(APPEND CMAKE_REQUIRED_DEFINITIONS -DLDAP_DEPRECATED=1)
+ list(APPEND CMAKE_REQUIRED_LIBRARIES ${CMAKE_LDAP_LIB})
+ if(HAVE_LIBLBER)
+ list(APPEND CMAKE_REQUIRED_LIBRARIES ${CMAKE_LBER_LIB})
+ endif()
+
+ check_c_source_compiles("
${_INCLUDE_STRING}
int main(int argc, char ** argv)
{
@@ -943,21 +981,27 @@ if(NOT CURL_DISABLE_LDAP)
BerElement *bep = ber_init(bvp);
ber_free(bep, 1);
return 0;
- }"
- )
- list(APPEND CMAKE_REQUIRED_DEFINITIONS -DLDAP_DEPRECATED=1)
- list(APPEND CMAKE_REQUIRED_LIBRARIES ${CMAKE_LDAP_LIB})
- if(HAVE_LIBLBER)
- list(APPEND CMAKE_REQUIRED_LIBRARIES ${CMAKE_LBER_LIB})
- endif()
- check_c_source_compiles("${_SRC_STRING}" NOT_NEED_LBER_H)
- unset(CMAKE_REQUIRED_LIBRARIES)
-
+ }" NOT_NEED_LBER_H)
if(NOT_NEED_LBER_H)
set(NEED_LBER_H OFF)
else()
set(CURL_TEST_DEFINES "${CURL_TEST_DEFINES} -DNEED_LBER_H")
endif()
+
+ check_function_exists(ldap_url_parse HAVE_LDAP_URL_PARSE)
+ check_function_exists(ldap_init_fd HAVE_LDAP_INIT_FD)
+
+ unset(CMAKE_REQUIRED_LIBRARIES)
+
+ check_include_file("ldap_ssl.h" HAVE_LDAP_SSL_H)
+
+ if(HAVE_LDAP_INIT_FD)
+ set(USE_OPENLDAP ON)
+ add_definitions("-DLDAP_DEPRECATED=1")
+ endif()
+ if(NOT CURL_DISABLE_LDAPS)
+ set(HAVE_LDAP_SSL ON)
+ endif()
endif()
endif()
endif()
@@ -970,10 +1014,6 @@ if(CURL_DISABLE_LDAP)
endif()
endif()
-if(NOT CURL_DISABLE_LDAPS)
- check_include_file_concat("ldap_ssl.h" HAVE_LDAP_SSL_H)
-endif()
-
# Check for idn2
option(USE_LIBIDN2 "Use libidn2 for IDN support" ON)
if(USE_LIBIDN2)
@@ -1180,9 +1220,13 @@ elseif(CURL_CA_PATH_AUTODETECT OR CURL_CA_BUNDLE_AUTODETECT)
endif()
endif()
-if(CURL_CA_PATH_SET AND NOT USE_OPENSSL AND NOT USE_MBEDTLS)
+if(CURL_CA_PATH_SET AND
+ NOT USE_OPENSSL AND
+ NOT USE_WOLFSSL AND
+ NOT USE_GNUTLS AND
+ NOT USE_MBEDTLS)
message(STATUS
- "CA path only supported by OpenSSL, GnuTLS or mbed TLS. "
+ "CA path only supported by OpenSSL, wolfSSL, GnuTLS or mbedTLS. "
"Set CURL_CA_PATH=none or enable one of those TLS backends.")
endif()
endif()
@@ -1200,6 +1244,7 @@ endif()
check_include_file_concat("inttypes.h" HAVE_INTTYPES_H)
check_include_file_concat("sys/filio.h" HAVE_SYS_FILIO_H)
+check_include_file_concat("sys/wait.h" HAVE_SYS_WAIT_H)
check_include_file_concat("sys/ioctl.h" HAVE_SYS_IOCTL_H)
check_include_file_concat("sys/param.h" HAVE_SYS_PARAM_H)
check_include_file_concat("sys/poll.h" HAVE_SYS_POLL_H)
@@ -1214,7 +1259,6 @@ check_include_file_concat("sys/un.h" HAVE_SYS_UN_H)
check_include_file_concat("sys/utime.h" HAVE_SYS_UTIME_H)
check_include_file_concat("sys/xattr.h" HAVE_SYS_XATTR_H)
check_include_file_concat("arpa/inet.h" HAVE_ARPA_INET_H)
-check_include_file_concat("arpa/tftp.h" HAVE_ARPA_TFTP_H)
check_include_file_concat("fcntl.h" HAVE_FCNTL_H)
check_include_file_concat("idn2.h" HAVE_IDN2_H)
check_include_file_concat("ifaddrs.h" HAVE_IFADDRS_H)
@@ -1225,30 +1269,29 @@ check_include_file_concat("net/if.h" HAVE_NET_IF_H)
check_include_file_concat("netdb.h" HAVE_NETDB_H)
check_include_file_concat("netinet/in.h" HAVE_NETINET_IN_H)
check_include_file_concat("netinet/tcp.h" HAVE_NETINET_TCP_H)
+check_include_file_concat("netinet/udp.h" HAVE_NETINET_UDP_H)
check_include_file("linux/tcp.h" HAVE_LINUX_TCP_H)
check_include_file_concat("poll.h" HAVE_POLL_H)
check_include_file_concat("pwd.h" HAVE_PWD_H)
-check_include_file_concat("setjmp.h" HAVE_SETJMP_H)
-check_include_file_concat("signal.h" HAVE_SIGNAL_H)
check_include_file_concat("stdatomic.h" HAVE_STDATOMIC_H)
check_include_file_concat("stdbool.h" HAVE_STDBOOL_H)
check_include_file_concat("stdint.h" HAVE_STDINT_H)
-check_include_file_concat("stdlib.h" HAVE_STDLIB_H)
-check_include_file_concat("string.h" HAVE_STRING_H)
check_include_file_concat("strings.h" HAVE_STRINGS_H)
check_include_file_concat("stropts.h" HAVE_STROPTS_H)
check_include_file_concat("termio.h" HAVE_TERMIO_H)
check_include_file_concat("termios.h" HAVE_TERMIOS_H)
-check_include_file_concat("time.h" HAVE_TIME_H)
check_include_file_concat("unistd.h" HAVE_UNISTD_H)
check_include_file_concat("utime.h" HAVE_UTIME_H)
-check_include_file_concat("stddef.h" HAVE_STDDEF_H)
-
check_type_size(size_t SIZEOF_SIZE_T)
check_type_size(ssize_t SIZEOF_SSIZE_T)
check_type_size("time_t" SIZEOF_TIME_T)
+check_type_size("suseconds_t" SIZEOF_SUSECONDS_T)
+
+if(SIZEOF_SUSECONDS_T)
+ set(HAVE_SUSECONDS_T 1)
+endif()
if(NOT CMAKE_CROSSCOMPILING)
find_file(RANDOM_FILE urandom /dev)
@@ -1265,45 +1308,50 @@ elseif(HAVE_LIBNETWORK)
endif()
check_symbol_exists(fchmod "${CURL_INCLUDES}" HAVE_FCHMOD)
-check_symbol_exists(basename "${CURL_INCLUDES}" HAVE_BASENAME)
+check_symbol_exists(fnmatch "${CURL_INCLUDES};fnmatch.h" HAVE_FNMATCH)
+check_symbol_exists(basename "${CURL_INCLUDES};string.h" HAVE_BASENAME)
check_symbol_exists(socket "${CURL_INCLUDES}" HAVE_SOCKET)
+check_symbol_exists(sched_yield "${CURL_INCLUDES};sched.h" HAVE_SCHED_YIELD)
check_symbol_exists(socketpair "${CURL_INCLUDES}" HAVE_SOCKETPAIR)
check_symbol_exists(recv "${CURL_INCLUDES}" HAVE_RECV)
check_symbol_exists(send "${CURL_INCLUDES}" HAVE_SEND)
check_symbol_exists(sendmsg "${CURL_INCLUDES}" HAVE_SENDMSG)
check_symbol_exists(select "${CURL_INCLUDES}" HAVE_SELECT)
-check_symbol_exists(strdup "${CURL_INCLUDES}" HAVE_STRDUP)
-check_symbol_exists(strtok_r "${CURL_INCLUDES}" HAVE_STRTOK_R)
-check_symbol_exists(strcasecmp "${CURL_INCLUDES}" HAVE_STRCASECMP)
-check_symbol_exists(stricmp "${CURL_INCLUDES}" HAVE_STRICMP)
-check_symbol_exists(strcmpi "${CURL_INCLUDES}" HAVE_STRCMPI)
+check_symbol_exists(strdup "${CURL_INCLUDES};string.h" HAVE_STRDUP)
+check_symbol_exists(strtok_r "${CURL_INCLUDES};string.h" HAVE_STRTOK_R)
+check_symbol_exists(strcasecmp "${CURL_INCLUDES};string.h" HAVE_STRCASECMP)
+check_symbol_exists(stricmp "${CURL_INCLUDES};string.h" HAVE_STRICMP)
+check_symbol_exists(strcmpi "${CURL_INCLUDES};string.h" HAVE_STRCMPI)
+check_symbol_exists(memrchr "${CURL_INCLUDES};string.h" HAVE_MEMRCHR)
check_symbol_exists(alarm "${CURL_INCLUDES}" HAVE_ALARM)
+check_symbol_exists(arc4random "${CURL_INCLUDES};stdlib.h" HAVE_ARC4RANDOM)
+check_symbol_exists(fcntl "${CURL_INCLUDES}" HAVE_FCNTL)
check_symbol_exists(getppid "${CURL_INCLUDES}" HAVE_GETPPID)
check_symbol_exists(utimes "${CURL_INCLUDES}" HAVE_UTIMES)
check_symbol_exists(gettimeofday "${CURL_INCLUDES}" HAVE_GETTIMEOFDAY)
check_symbol_exists(closesocket "${CURL_INCLUDES}" HAVE_CLOSESOCKET)
-check_symbol_exists(sigsetjmp "${CURL_INCLUDES}" HAVE_SIGSETJMP)
+check_symbol_exists(sigsetjmp "${CURL_INCLUDES};setjmp.h" HAVE_SIGSETJMP)
check_symbol_exists(getpass_r "${CURL_INCLUDES}" HAVE_GETPASS_R)
check_symbol_exists(getpwuid "${CURL_INCLUDES}" HAVE_GETPWUID)
check_symbol_exists(getpwuid_r "${CURL_INCLUDES}" HAVE_GETPWUID_R)
check_symbol_exists(geteuid "${CURL_INCLUDES}" HAVE_GETEUID)
check_symbol_exists(utime "${CURL_INCLUDES}" HAVE_UTIME)
-check_symbol_exists(gmtime_r "${CURL_INCLUDES}" HAVE_GMTIME_R)
+check_symbol_exists(gmtime_r "${CURL_INCLUDES};stdlib.h;time.h" HAVE_GMTIME_R)
check_symbol_exists(gethostbyname_r "${CURL_INCLUDES}" HAVE_GETHOSTBYNAME_R)
-check_symbol_exists(signal "${CURL_INCLUDES}" HAVE_SIGNAL)
-check_symbol_exists(strtoll "${CURL_INCLUDES}" HAVE_STRTOLL)
-check_symbol_exists(strerror_r "${CURL_INCLUDES}" HAVE_STRERROR_R)
-check_symbol_exists(siginterrupt "${CURL_INCLUDES}" HAVE_SIGINTERRUPT)
-check_symbol_exists(getaddrinfo "${CURL_INCLUDES}" HAVE_GETADDRINFO)
-if(WIN32)
- set(HAVE_GETADDRINFO_THREADSAFE ${HAVE_GETADDRINFO})
-endif()
+check_symbol_exists(signal "${CURL_INCLUDES};signal.h" HAVE_SIGNAL)
+check_symbol_exists(strtoll "${CURL_INCLUDES};stdlib.h" HAVE_STRTOLL)
+check_symbol_exists(strerror_r "${CURL_INCLUDES};stdlib.h;string.h" HAVE_STRERROR_R)
+check_symbol_exists(siginterrupt "${CURL_INCLUDES};signal.h" HAVE_SIGINTERRUPT)
+check_symbol_exists(getaddrinfo "${CURL_INCLUDES};stdlib.h;string.h" HAVE_GETADDRINFO)
+check_symbol_exists(getifaddrs "${CURL_INCLUDES};stdlib.h" HAVE_GETIFADDRS)
check_symbol_exists(freeaddrinfo "${CURL_INCLUDES}" HAVE_FREEADDRINFO)
check_symbol_exists(pipe "${CURL_INCLUDES}" HAVE_PIPE)
check_symbol_exists(ftruncate "${CURL_INCLUDES}" HAVE_FTRUNCATE)
+check_symbol_exists(fseeko "${CURL_INCLUDES};stdio.h" HAVE_FSEEKO)
+check_symbol_exists(_fseeki64 "${CURL_INCLUDES};stdio.h" HAVE__FSEEKI64)
check_symbol_exists(getpeername "${CURL_INCLUDES}" HAVE_GETPEERNAME)
check_symbol_exists(getsockname "${CURL_INCLUDES}" HAVE_GETSOCKNAME)
check_symbol_exists(if_nametoindex "${CURL_INCLUDES}" HAVE_IF_NAMETOINDEX)
@@ -1317,11 +1365,11 @@ if(NOT MSVC OR (MSVC_VERSION GREATER_EQUAL 1900))
check_symbol_exists(snprintf "stdio.h" HAVE_SNPRINTF)
endif()
check_function_exists(mach_absolute_time HAVE_MACH_ABSOLUTE_TIME)
-check_symbol_exists(inet_ntop "${CURL_INCLUDES}" HAVE_INET_NTOP)
+check_symbol_exists(inet_ntop "${CURL_INCLUDES};stdlib.h;string.h" HAVE_INET_NTOP)
if(MSVC AND (MSVC_VERSION LESS_EQUAL 1600))
set(HAVE_INET_NTOP OFF)
endif()
-check_symbol_exists(inet_pton "${CURL_INCLUDES}" HAVE_INET_PTON)
+check_symbol_exists(inet_pton "${CURL_INCLUDES};stdlib.h;string.h" HAVE_INET_PTON)
check_symbol_exists(fsetxattr "${CURL_INCLUDES}" HAVE_FSETXATTR)
if(HAVE_FSETXATTR)
@@ -1342,24 +1390,15 @@ set(CMAKE_EXTRA_INCLUDE_FILES "")
# sigaction and sigsetjmp are special. Use special mechanism for
# detecting those, but only if previous attempt failed.
-if(HAVE_SIGNAL_H)
- check_symbol_exists(sigaction "signal.h" HAVE_SIGACTION)
-endif()
+check_symbol_exists(sigaction "signal.h" HAVE_SIGACTION)
if(NOT HAVE_SIGSETJMP)
- if(HAVE_SETJMP_H)
- check_symbol_exists(sigsetjmp "setjmp.h" HAVE_MACRO_SIGSETJMP)
- if(HAVE_MACRO_SIGSETJMP)
- set(HAVE_SIGSETJMP 1)
- endif()
+ check_symbol_exists(sigsetjmp "setjmp.h" HAVE_MACRO_SIGSETJMP)
+ if(HAVE_MACRO_SIGSETJMP)
+ set(HAVE_SIGSETJMP 1)
endif()
endif()
-# If there is no stricmp(), do not allow LDAP to parse URLs
-if(NOT HAVE_STRICMP)
- set(HAVE_LDAP_URL_PARSE 1)
-endif()
-
# Do curl specific tests
foreach(CURL_TEST
HAVE_FCNTL_O_NONBLOCK
@@ -1370,7 +1409,6 @@ foreach(CURL_TEST
HAVE_IOCTL_FIONBIO
HAVE_IOCTL_SIOCGIFADDR
HAVE_SETSOCKOPT_SO_NONBLOCK
- TIME_WITH_SYS_TIME
HAVE_O_NONBLOCK
HAVE_GETHOSTBYNAME_R_3
HAVE_GETHOSTBYNAME_R_5
@@ -1415,6 +1453,18 @@ if(WIN32)
unset(HAVE_WIN32_WINNT CACHE)
endif()
+if(NOT WIN32 AND NOT CMAKE_CROSSCOMPILING)
+ # on not-Windows and not-crosscompiling, check for writable argv[]
+ include(CheckCSourceRuns)
+ check_c_source_runs("
+ int main(int argc, char **argv)
+ {
+ (void)argc;
+ argv[0][0] = ' ';
+ return (argv[0][0] == ' ')?0:1;
+ }" HAVE_WRITABLE_ARGV)
+endif()
+
set(CMAKE_REQUIRED_FLAGS)
option(ENABLE_WEBSOCKETS "Set to ON to enable EXPERIMENTAL websockets" OFF)
@@ -1525,11 +1575,7 @@ if(WIN32)
list(APPEND CURL_LIBS "advapi32" "crypt32")
endif()
- if(NOT HAVE_MINGW_ORIGINAL)
- list(APPEND CURL_LIBS "bcrypt")
- else()
- set(HAVE_FTRUNCATE OFF)
- endif()
+ list(APPEND CURL_LIBS "bcrypt")
endif()
if(MSVC)
@@ -1644,7 +1690,7 @@ macro(_add_if label)
endmacro()
# NTLM support requires crypto function adaptions from various SSL libs
-# TODO alternative SSL libs tests for SSP1, GNUTLS, NSS
+# TODO alternative SSL libs tests for SSP1, GnuTLS, NSS
if(NOT (CURL_DISABLE_NTLM) AND
(USE_OPENSSL OR USE_MBEDTLS OR USE_DARWINSSL OR USE_WIN32_CRYPTO OR USE_GNUTLS))
set(use_curl_ntlm_core ON)
@@ -1673,14 +1719,13 @@ _add_if("SPNEGO" NOT CURL_DISABLE_NEGOTIATE_AUTH AND
_add_if("Kerberos" NOT CURL_DISABLE_KERBEROS_AUTH AND
(HAVE_GSSAPI OR USE_WINDOWS_SSPI))
# NTLM support requires crypto function adaptions from various SSL libs
-# TODO alternative SSL libs tests for SSP1, GNUTLS, NSS
+# TODO alternative SSL libs tests for SSP1, GnuTLS, NSS
_add_if("NTLM" NOT (CURL_DISABLE_NTLM) AND
(use_curl_ntlm_core OR USE_WINDOWS_SSPI))
# TODO missing option (autoconf: --enable-ntlm-wb)
_add_if("NTLM_WB" NOT (CURL_DISABLE_NTLM) AND
(use_curl_ntlm_core OR USE_WINDOWS_SSPI) AND
NOT CURL_DISABLE_HTTP AND NTLM_WB_ENABLED)
-# TODO missing option (--enable-tls-srp), depends on GNUTLS_SRP/OPENSSL_SRP
_add_if("TLS-SRP" USE_TLS_SRP)
# TODO option --with-nghttp2 tests for nghttp2 lib and nghttp2/nghttp2.h header
_add_if("HTTP2" USE_NGHTTP2)
@@ -1707,7 +1752,6 @@ _add_if("FILE" NOT CURL_DISABLE_FILE)
_add_if("TELNET" NOT CURL_DISABLE_TELNET)
_add_if("LDAP" NOT CURL_DISABLE_LDAP)
# CURL_DISABLE_LDAP implies CURL_DISABLE_LDAPS
-# TODO check HAVE_LDAP_SSL (in autoconf this is enabled with --enable-ldaps)
_add_if("LDAPS" NOT CURL_DISABLE_LDAPS AND
((USE_OPENLDAP AND SSL_ENABLED) OR
(NOT USE_OPENLDAP AND HAVE_LDAP_SSL)))
diff --git a/Utilities/cmcurl/include/curl/curl.h b/Utilities/cmcurl/include/curl/curl.h
index d3ebb3b..0496570 100644
--- a/Utilities/cmcurl/include/curl/curl.h
+++ b/Utilities/cmcurl/include/curl/curl.h
@@ -159,7 +159,7 @@ typedef enum {
CURLSSLBACKEND_NONE = 0,
CURLSSLBACKEND_OPENSSL = 1,
CURLSSLBACKEND_GNUTLS = 2,
- CURLSSLBACKEND_NSS = 3,
+ CURLSSLBACKEND_NSS CURL_DEPRECATED(8.3.0, "") = 3,
CURLSSLBACKEND_OBSOLETE4 = 4, /* Was QSOSSL. */
CURLSSLBACKEND_GSKIT CURL_DEPRECATED(8.3.0, "") = 5,
CURLSSLBACKEND_POLARSSL CURL_DEPRECATED(7.69.0, "") = 6,
@@ -646,10 +646,10 @@ typedef enum {
#ifndef CURL_NO_OLDIES /* define this to test if your app builds with all
the obsolete stuff removed! */
-/* Previously obsolete error code re-used in 7.38.0 */
+/* Previously obsolete error code reused in 7.38.0 */
#define CURLE_OBSOLETE16 CURLE_HTTP2
-/* Previously obsolete error codes re-used in 7.24.0 */
+/* Previously obsolete error codes reused in 7.24.0 */
#define CURLE_OBSOLETE10 CURLE_FTP_ACCEPT_FAILED
#define CURLE_OBSOLETE12 CURLE_FTP_ACCEPT_TIMEOUT
@@ -1358,7 +1358,7 @@ typedef enum {
operation slower and is less friendly for the network. */
CURLOPT(CURLOPT_FRESH_CONNECT, CURLOPTTYPE_LONG, 74),
- /* Set to explicitly forbid the upcoming transfer's connection to be re-used
+ /* Set to explicitly forbid the upcoming transfer's connection to be reused
when done. Do not use this unless you're absolutely sure of this, as it
makes the operation slower and is less friendly for the network. */
CURLOPT(CURLOPT_FORBID_REUSE, CURLOPTTYPE_LONG, 75),
@@ -1652,7 +1652,7 @@ typedef enum {
CURLOPT(CURLOPT_SOCKOPTFUNCTION, CURLOPTTYPE_FUNCTIONPOINT, 148),
CURLOPT(CURLOPT_SOCKOPTDATA, CURLOPTTYPE_CBPOINT, 149),
- /* set to 0 to disable session ID re-use for this transfer, default is
+ /* set to 0 to disable session ID reuse for this transfer, default is
enabled (== 1) */
CURLOPT(CURLOPT_SSL_SESSIONID_CACHE, CURLOPTTYPE_LONG, 150),
diff --git a/Utilities/cmcurl/include/curl/curlver.h b/Utilities/cmcurl/include/curl/curlver.h
index 7004fad..3c3f992 100644
--- a/Utilities/cmcurl/include/curl/curlver.h
+++ b/Utilities/cmcurl/include/curl/curlver.h
@@ -32,12 +32,12 @@
/* This is the version number of the libcurl package from which this header
file origins: */
-#define LIBCURL_VERSION "8.3.0"
+#define LIBCURL_VERSION "8.4.0"
/* The numeric version number is also available "in parts" by using these
defines: */
#define LIBCURL_VERSION_MAJOR 8
-#define LIBCURL_VERSION_MINOR 3
+#define LIBCURL_VERSION_MINOR 4
#define LIBCURL_VERSION_PATCH 0
/* This is the numeric version of the libcurl version number, meant for easier
@@ -59,7 +59,7 @@
CURL_VERSION_BITS() macro since curl's own configure script greps for it
and needs it to contain the full number.
*/
-#define LIBCURL_VERSION_NUM 0x080300
+#define LIBCURL_VERSION_NUM 0x080400
/*
* This is the date and time when the full source package was created. The
diff --git a/Utilities/cmcurl/include/curl/multi.h b/Utilities/cmcurl/include/curl/multi.h
index 13b55b7..e79b48f 100644
--- a/Utilities/cmcurl/include/curl/multi.h
+++ b/Utilities/cmcurl/include/curl/multi.h
@@ -426,6 +426,17 @@ CURL_EXTERN CURLMcode curl_multi_setopt(CURLM *multi_handle,
CURL_EXTERN CURLMcode curl_multi_assign(CURLM *multi_handle,
curl_socket_t sockfd, void *sockp);
+/*
+ * Name: curl_multi_get_handles()
+ *
+ * Desc: Returns an allocated array holding all handles currently added to
+ * the multi handle. Marks the final entry with a NULL pointer. If
+ * there is no easy handle added to the multi handle, this function
+ * returns an array with the first entry as a NULL pointer.
+ *
+ * Returns: NULL on failure, otherwise a CURL **array pointer
+ */
+CURL_EXTERN CURL **curl_multi_get_handles(CURLM *multi_handle);
/*
* Name: curl_push_callback
diff --git a/Utilities/cmcurl/lib/CMakeLists.txt b/Utilities/cmcurl/lib/CMakeLists.txt
index c4c6956..9899b9d 100644
--- a/Utilities/cmcurl/lib/CMakeLists.txt
+++ b/Utilities/cmcurl/lib/CMakeLists.txt
@@ -94,9 +94,9 @@ add_library(
target_compile_definitions(curlu PUBLIC UNITTESTS CURL_STATICLIB)
if(ENABLE_CURLDEBUG)
- # We must compile memdebug.c separately to avoid memdebug.h redefinitions
- # being applied to memdebug.c itself.
- set_source_files_properties(memdebug.c PROPERTIES SKIP_UNITY_BUILD_INCLUSION ON)
+ # We must compile these sources separately to avoid memdebug.h redefinitions
+ # applying to them.
+ set_source_files_properties(memdebug.c curl_multibyte.c PROPERTIES SKIP_UNITY_BUILD_INCLUSION ON)
endif()
target_link_libraries(curlu PRIVATE ${CURL_LIBS})
@@ -123,19 +123,6 @@ else()
unset(CMAKESONAME)
endif()
-if(NOT WIN32 AND NOT CMAKE_CROSSCOMPILING)
- # on not-Windows and not-crosscompiling, check for writable argv[]
- include(CheckCSourceRuns)
- check_c_source_runs("
-int main(int argc, char **argv)
-{
- (void)argc;
- argv[0][0] = ' ';
- return (argv[0][0] == ' ')?0:1;
-}"
- HAVE_WRITABLE_ARGV)
-endif()
-
## Library definition
# Add "_imp" as a suffix before the extension to avoid conflicting with
@@ -160,18 +147,23 @@ if(NOT DEFINED SHARE_LIB_OBJECT)
endif()
endif()
+if(WIN32)
+ # Define CURL_STATICLIB always, to disable __declspec(dllexport) for exported
+ # libcurl symbols. We handle exports via libcurl.def instead. Except with
+ # symbol hiding disabled or debug mode enabled, when we export _all_ symbols
+ # from libcurl DLL, without using libcurl.def.
+ add_definitions("-DCURL_STATICLIB")
+endif()
+
if(SHARE_LIB_OBJECT)
set(LIB_OBJECT "libcurl_object")
add_library(${LIB_OBJECT} OBJECT ${HHEADERS} ${CSOURCES})
target_link_libraries(${LIB_OBJECT} PRIVATE ${CURL_LIBS})
set_target_properties(${LIB_OBJECT} PROPERTIES
- COMPILE_DEFINITIONS "BUILDING_LIBCURL"
- INTERFACE_COMPILE_DEFINITIONS "CURL_STATICLIB"
POSITION_INDEPENDENT_CODE ON)
if(HIDES_CURL_PRIVATE_SYMBOLS)
- set_target_properties(${LIB_OBJECT} PROPERTIES
- COMPILE_DEFINITIONS "CURL_HIDDEN_SYMBOLS"
- COMPILE_FLAGS "${CURL_CFLAG_SYMBOLS_HIDE}")
+ set_property(TARGET ${LIB_OBJECT} APPEND PROPERTY COMPILE_FLAGS "${CURL_CFLAG_SYMBOLS_HIDE}")
+ set_property(TARGET ${LIB_OBJECT} APPEND PROPERTY COMPILE_DEFINITIONS "CURL_HIDDEN_SYMBOLS")
endif()
if(CURL_HAS_LTO)
set_target_properties(${LIB_OBJECT} PROPERTIES
@@ -198,12 +190,10 @@ if(BUILD_STATIC_LIBS)
set_target_properties(${LIB_STATIC} PROPERTIES
PREFIX "" OUTPUT_NAME "${LIBCURL_OUTPUT_NAME}"
SUFFIX "${STATIC_LIB_SUFFIX}${CMAKE_STATIC_LIBRARY_SUFFIX}"
- COMPILE_DEFINITIONS "BUILDING_LIBCURL"
INTERFACE_COMPILE_DEFINITIONS "CURL_STATICLIB")
if(HIDES_CURL_PRIVATE_SYMBOLS)
- set_target_properties(${LIB_STATIC} PROPERTIES
- COMPILE_DEFINITIONS "CURL_HIDDEN_SYMBOLS"
- COMPILE_FLAGS "${CURL_CFLAG_SYMBOLS_HIDE}")
+ set_property(TARGET ${LIB_STATIC} APPEND PROPERTY COMPILE_FLAGS "${CURL_CFLAG_SYMBOLS_HIDE}")
+ set_property(TARGET ${LIB_STATIC} APPEND PROPERTY COMPILE_DEFINITIONS "CURL_HIDDEN_SYMBOLS")
endif()
if(CURL_HAS_LTO)
set_target_properties(${LIB_STATIC} PROPERTIES
@@ -225,19 +215,20 @@ if(BUILD_SHARED_LIBS)
add_library(${LIB_SHARED} SHARED ${LIB_SOURCE})
add_library(${PROJECT_NAME}::${LIB_SHARED} ALIAS ${LIB_SHARED})
if(WIN32)
- set_property(TARGET ${LIB_SHARED} APPEND PROPERTY SOURCES libcurl.rc ${CURL_SOURCE_DIR}/libcurl.def)
+ set_property(TARGET ${LIB_SHARED} APPEND PROPERTY SOURCES libcurl.rc)
+ if(HIDES_CURL_PRIVATE_SYMBOLS)
+ set_property(TARGET ${LIB_SHARED} APPEND PROPERTY SOURCES "${CURL_SOURCE_DIR}/libcurl.def")
+ endif()
endif()
target_link_libraries(${LIB_SHARED} PRIVATE ${CURL_LIBS})
# Remove the "lib" prefix since the library is already named "libcurl".
set_target_properties(${LIB_SHARED} PROPERTIES
PREFIX "" OUTPUT_NAME "${LIBCURL_OUTPUT_NAME}"
IMPORT_PREFIX "" IMPORT_SUFFIX "${IMPORT_LIB_SUFFIX}${CMAKE_IMPORT_LIBRARY_SUFFIX}"
- COMPILE_DEFINITIONS "BUILDING_LIBCURL"
POSITION_INDEPENDENT_CODE ON)
if(HIDES_CURL_PRIVATE_SYMBOLS)
- set_target_properties(${LIB_SHARED} PROPERTIES
- COMPILE_DEFINITIONS "CURL_HIDDEN_SYMBOLS"
- COMPILE_FLAGS "${CURL_CFLAG_SYMBOLS_HIDE}")
+ set_property(TARGET ${LIB_SHARED} APPEND PROPERTY COMPILE_FLAGS "${CURL_CFLAG_SYMBOLS_HIDE}")
+ set_property(TARGET ${LIB_SHARED} APPEND PROPERTY COMPILE_DEFINITIONS "CURL_HIDDEN_SYMBOLS")
endif()
if(CURL_HAS_LTO)
set_target_properties(${LIB_SHARED} PROPERTIES
diff --git a/Utilities/cmcurl/lib/Makefile.inc b/Utilities/cmcurl/lib/Makefile.inc
index a08180b..e568ef9 100644
--- a/Utilities/cmcurl/lib/Makefile.inc
+++ b/Utilities/cmcurl/lib/Makefile.inc
@@ -162,12 +162,12 @@ LIB_CFILES = \
http.c \
http1.c \
http2.c \
+ http_aws_sigv4.c \
http_chunks.c \
http_digest.c \
http_negotiate.c \
http_ntlm.c \
http_proxy.c \
- http_aws_sigv4.c \
idn.c \
if2ip.c \
imap.c \
@@ -289,9 +289,9 @@ LIB_HFILES = \
fileinfo.h \
fopen.h \
formdata.h \
- functypes.h \
ftp.h \
ftplistparser.h \
+ functypes.h \
getinfo.h \
gopher.h \
hash.h \
@@ -301,12 +301,12 @@ LIB_HFILES = \
http.h \
http1.h \
http2.h \
+ http_aws_sigv4.h \
http_chunks.h \
http_digest.h \
http_negotiate.h \
http_ntlm.h \
http_proxy.h \
- http_aws_sigv4.h \
idn.h \
if2ip.h \
imap.h \
diff --git a/Utilities/cmcurl/lib/base64.c b/Utilities/cmcurl/lib/base64.c
index 30db7e5..2a49b5a 100644
--- a/Utilities/cmcurl/lib/base64.c
+++ b/Utilities/cmcurl/lib/base64.c
@@ -31,7 +31,7 @@
!defined(CURL_DISABLE_SMTP) || \
!defined(CURL_DISABLE_POP3) || \
!defined(CURL_DISABLE_IMAP) || \
- !defined(CURL_DISABLE_DOH) || defined(USE_SSL)
+ !defined(CURL_DISABLE_DOH) || defined(USE_SSL) || defined(BUILDING_CURL)
#include "curl/curl.h"
#include "warnless.h"
#include "curl_base64.h"
diff --git a/Utilities/cmcurl/lib/bufq.c b/Utilities/cmcurl/lib/bufq.c
index 1555449..d03906d 100644
--- a/Utilities/cmcurl/lib/bufq.c
+++ b/Utilities/cmcurl/lib/bufq.c
@@ -144,21 +144,6 @@ static size_t chunk_skip(struct buf_chunk *chunk, size_t amount)
return n;
}
-static void chunk_shift(struct buf_chunk *chunk)
-{
- if(chunk->r_offset) {
- if(!chunk_is_empty(chunk)) {
- size_t n = chunk->w_offset - chunk->r_offset;
- memmove(chunk->x.data, chunk->x.data + chunk->r_offset, n);
- chunk->w_offset -= chunk->r_offset;
- chunk->r_offset = 0;
- }
- else {
- chunk->r_offset = chunk->w_offset = 0;
- }
- }
-}
-
static void chunk_list_free(struct buf_chunk **anchor)
{
struct buf_chunk *chunk;
@@ -504,13 +489,6 @@ void Curl_bufq_skip(struct bufq *q, size_t amount)
}
}
-void Curl_bufq_skip_and_shift(struct bufq *q, size_t amount)
-{
- Curl_bufq_skip(q, amount);
- if(q->tail)
- chunk_shift(q->tail);
-}
-
ssize_t Curl_bufq_pass(struct bufq *q, Curl_bufq_writer *writer,
void *writer_ctx, CURLcode *err)
{
diff --git a/Utilities/cmcurl/lib/bufq.h b/Utilities/cmcurl/lib/bufq.h
index 89b5c84..089d61b 100644
--- a/Utilities/cmcurl/lib/bufq.h
+++ b/Utilities/cmcurl/lib/bufq.h
@@ -209,12 +209,6 @@ bool Curl_bufq_peek_at(struct bufq *q, size_t offset,
*/
void Curl_bufq_skip(struct bufq *q, size_t amount);
-/**
- * Same as `skip` but shift tail data to the start afterwards,
- * so that further writes will find room in tail.
- */
-void Curl_bufq_skip_and_shift(struct bufq *q, size_t amount);
-
typedef ssize_t Curl_bufq_writer(void *writer_ctx,
const unsigned char *buf, size_t len,
CURLcode *err);
diff --git a/Utilities/cmcurl/lib/c-hyper.c b/Utilities/cmcurl/lib/c-hyper.c
index 61ca29a..5726ff1 100644
--- a/Utilities/cmcurl/lib/c-hyper.c
+++ b/Utilities/cmcurl/lib/c-hyper.c
@@ -174,8 +174,6 @@ static int hyper_each_header(void *userdata,
if(!data->state.hconnect || !data->set.suppress_connect_headers) {
writetype = CLIENTWRITE_HEADER;
- if(data->set.include_header)
- writetype |= CLIENTWRITE_BODY;
if(data->state.hconnect)
writetype |= CLIENTWRITE_CONNECT;
if(data->req.httpcode/100 == 1)
@@ -248,11 +246,7 @@ static int hyper_body_chunk(void *userdata, const hyper_buf *chunk)
if(0 == len)
return HYPER_ITER_CONTINUE;
Curl_debug(data, CURLINFO_DATA_IN, buf, len);
- if(!data->set.http_ce_skip && k->writer_stack)
- /* content-encoded data */
- result = Curl_unencode_write(data, k->writer_stack, buf, len);
- else
- result = Curl_client_write(data, CLIENTWRITE_BODY, buf, len);
+ result = Curl_client_write(data, CLIENTWRITE_BODY, buf, len);
if(result) {
data->state.hresult = result;
@@ -260,7 +254,11 @@ static int hyper_body_chunk(void *userdata, const hyper_buf *chunk)
}
data->req.bytecount += len;
- Curl_pgrsSetDownloadCounter(data, data->req.bytecount);
+ result = Curl_pgrsSetDownloadCounter(data, data->req.bytecount);
+ if(result) {
+ data->state.hresult = result;
+ return HYPER_ITER_BREAK;
+ }
return HYPER_ITER_CONTINUE;
}
@@ -314,8 +312,6 @@ static CURLcode status_line(struct Curl_easy *data,
if(!data->state.hconnect || !data->set.suppress_connect_headers) {
writetype = CLIENTWRITE_HEADER|CLIENTWRITE_STATUS;
- if(data->set.include_header)
- writetype |= CLIENTWRITE_BODY;
result = Curl_client_write(data, writetype,
Curl_dyn_ptr(&data->state.headerb), len);
if(result)
diff --git a/Utilities/cmcurl/lib/cf-h1-proxy.c b/Utilities/cmcurl/lib/cf-h1-proxy.c
index e9bc13d..6748021 100644
--- a/Utilities/cmcurl/lib/cf-h1-proxy.c
+++ b/Utilities/cmcurl/lib/cf-h1-proxy.c
@@ -34,6 +34,7 @@
#include "dynbuf.h"
#include "sendf.h"
#include "http.h"
+#include "http1.h"
#include "http_proxy.h"
#include "url.h"
#include "select.h"
@@ -64,13 +65,10 @@ typedef enum {
/* struct for HTTP CONNECT tunneling */
struct h1_tunnel_state {
- int sockindex;
- const char *hostname;
- int remote_port;
struct HTTP CONNECT;
struct dynbuf rcvbuf;
- struct dynbuf req;
- size_t nsend;
+ struct dynbuf request_data;
+ size_t nsent;
size_t headerlines;
enum keeponval {
KEEPON_DONE,
@@ -94,46 +92,31 @@ static bool tunnel_is_failed(struct h1_tunnel_state *ts)
return ts && (ts->tunnel_state == H1_TUNNEL_FAILED);
}
-static CURLcode tunnel_reinit(struct h1_tunnel_state *ts,
- struct connectdata *conn,
- struct Curl_easy *data)
+static CURLcode tunnel_reinit(struct Curl_cfilter *cf,
+ struct Curl_easy *data,
+ struct h1_tunnel_state *ts)
{
(void)data;
+ (void)cf;
DEBUGASSERT(ts);
Curl_dyn_reset(&ts->rcvbuf);
- Curl_dyn_reset(&ts->req);
+ Curl_dyn_reset(&ts->request_data);
ts->tunnel_state = H1_TUNNEL_INIT;
ts->keepon = KEEPON_CONNECT;
ts->cl = 0;
ts->close_connection = FALSE;
-
- if(conn->bits.conn_to_host)
- ts->hostname = conn->conn_to_host.name;
- else if(ts->sockindex == SECONDARYSOCKET)
- ts->hostname = conn->secondaryhostname;
- else
- ts->hostname = conn->host.name;
-
- if(ts->sockindex == SECONDARYSOCKET)
- ts->remote_port = conn->secondary_port;
- else if(conn->bits.conn_to_port)
- ts->remote_port = conn->conn_to_port;
- else
- ts->remote_port = conn->remote_port;
-
return CURLE_OK;
}
-static CURLcode tunnel_init(struct h1_tunnel_state **pts,
+static CURLcode tunnel_init(struct Curl_cfilter *cf,
struct Curl_easy *data,
- struct connectdata *conn,
- int sockindex)
+ struct h1_tunnel_state **pts)
{
struct h1_tunnel_state *ts;
CURLcode result;
- if(conn->handler->flags & PROTOPT_NOTCPPROXY) {
- failf(data, "%s cannot be done over CONNECT", conn->handler->scheme);
+ if(cf->conn->handler->flags & PROTOPT_NOTCPPROXY) {
+ failf(data, "%s cannot be done over CONNECT", cf->conn->handler->scheme);
return CURLE_UNSUPPORTED_PROTOCOL;
}
@@ -146,15 +129,14 @@ static CURLcode tunnel_init(struct h1_tunnel_state **pts,
if(!ts)
return CURLE_OUT_OF_MEMORY;
- ts->sockindex = sockindex;
infof(data, "allocate connect buffer");
Curl_dyn_init(&ts->rcvbuf, DYN_PROXY_CONNECT_HEADERS);
- Curl_dyn_init(&ts->req, DYN_HTTP_REQUEST);
+ Curl_dyn_init(&ts->request_data, DYN_HTTP_REQUEST);
*pts = ts;
- connkeep(conn, "HTTP proxy CONNECT");
- return tunnel_reinit(ts, conn, data);
+ connkeep(cf->conn, "HTTP proxy CONNECT");
+ return tunnel_reinit(cf, data, ts);
}
static void h1_tunnel_go_state(struct Curl_cfilter *cf,
@@ -176,7 +158,7 @@ static void h1_tunnel_go_state(struct Curl_cfilter *cf,
switch(new_state) {
case H1_TUNNEL_INIT:
CURL_TRC_CF(data, cf, "new tunnel state 'init'");
- tunnel_reinit(ts, cf->conn, data);
+ tunnel_reinit(cf, data, ts);
break;
case H1_TUNNEL_CONNECT:
@@ -207,7 +189,7 @@ static void h1_tunnel_go_state(struct Curl_cfilter *cf,
CURL_TRC_CF(data, cf, "new tunnel state 'failed'");
ts->tunnel_state = new_state;
Curl_dyn_reset(&ts->rcvbuf);
- Curl_dyn_reset(&ts->req);
+ Curl_dyn_reset(&ts->request_data);
/* restore the protocol pointer */
data->info.httpcode = 0; /* clear it as it might've been used for the
proxy */
@@ -229,171 +211,80 @@ static void tunnel_free(struct Curl_cfilter *cf,
if(ts) {
h1_tunnel_go_state(cf, ts, H1_TUNNEL_FAILED, data);
Curl_dyn_free(&ts->rcvbuf);
- Curl_dyn_free(&ts->req);
+ Curl_dyn_free(&ts->request_data);
free(ts);
cf->ctx = NULL;
}
}
-static CURLcode CONNECT_host(struct Curl_easy *data,
- struct connectdata *conn,
- const char *hostname,
- int remote_port,
- char **connecthostp,
- char **hostp)
-{
- char *hostheader; /* for CONNECT */
- char *host = NULL; /* Host: */
- bool ipv6_ip = conn->bits.ipv6_ip;
-
- /* the hostname may be different */
- if(hostname != conn->host.name)
- ipv6_ip = (strchr(hostname, ':') != NULL);
- hostheader = /* host:port with IPv6 support */
- aprintf("%s%s%s:%d", ipv6_ip?"[":"", hostname, ipv6_ip?"]":"",
- remote_port);
- if(!hostheader)
- return CURLE_OUT_OF_MEMORY;
-
- if(!Curl_checkProxyheaders(data, conn, STRCONST("Host"))) {
- host = aprintf("Host: %s\r\n", hostheader);
- if(!host) {
- free(hostheader);
- return CURLE_OUT_OF_MEMORY;
- }
- }
- *connecthostp = hostheader;
- *hostp = host;
- return CURLE_OK;
-}
-
#ifndef USE_HYPER
static CURLcode start_CONNECT(struct Curl_cfilter *cf,
struct Curl_easy *data,
struct h1_tunnel_state *ts)
{
- struct connectdata *conn = cf->conn;
- char *hostheader = NULL;
- char *host = NULL;
- const char *httpv;
+ struct httpreq *req = NULL;
+ int http_minor;
CURLcode result;
- infof(data, "Establish HTTP proxy tunnel to %s:%d",
- ts->hostname, ts->remote_port);
-
/* This only happens if we've looped here due to authentication
reasons, and we don't really use the newly cloned URL here
then. Just free() it. */
Curl_safefree(data->req.newurl);
- result = CONNECT_host(data, conn,
- ts->hostname, ts->remote_port,
- &hostheader, &host);
- if(result)
- goto out;
-
- /* Setup the proxy-authorization header, if any */
- result = Curl_http_output_auth(data, conn, "CONNECT", HTTPREQ_GET,
- hostheader, TRUE);
- if(result)
- goto out;
-
- httpv = (conn->http_proxy.proxytype == CURLPROXY_HTTP_1_0) ? "1.0" : "1.1";
-
- result =
- Curl_dyn_addf(&ts->req,
- "CONNECT %s HTTP/%s\r\n"
- "%s" /* Host: */
- "%s", /* Proxy-Authorization */
- hostheader,
- httpv,
- host?host:"",
- data->state.aptr.proxyuserpwd?
- data->state.aptr.proxyuserpwd:"");
+ result = Curl_http_proxy_create_CONNECT(&req, cf, data, 1);
if(result)
goto out;
- if(!Curl_checkProxyheaders(data, conn, STRCONST("User-Agent"))
- && data->set.str[STRING_USERAGENT])
- result = Curl_dyn_addf(&ts->req, "User-Agent: %s\r\n",
- data->set.str[STRING_USERAGENT]);
- if(result)
- goto out;
-
- if(!Curl_checkProxyheaders(data, conn, STRCONST("Proxy-Connection")))
- result = Curl_dyn_addn(&ts->req,
- STRCONST("Proxy-Connection: Keep-Alive\r\n"));
- if(result)
- goto out;
-
- result = Curl_add_custom_headers(data, TRUE, &ts->req);
- if(result)
- goto out;
+ infof(data, "Establish HTTP proxy tunnel to %s", req->authority);
- /* CRLF terminate the request */
- result = Curl_dyn_addn(&ts->req, STRCONST("\r\n"));
- if(result)
- goto out;
-
- /* Send the connect request to the proxy */
- result = Curl_buffer_send(&ts->req, data, &ts->CONNECT,
- &data->info.request_size, 0,
- ts->sockindex);
+ Curl_dyn_reset(&ts->request_data);
+ ts->nsent = 0;
ts->headerlines = 0;
+ http_minor = (cf->conn->http_proxy.proxytype == CURLPROXY_HTTP_1_0) ? 0 : 1;
+
+ result = Curl_h1_req_write_head(req, http_minor, &ts->request_data);
out:
if(result)
failf(data, "Failed sending CONNECT to proxy");
- free(host);
- free(hostheader);
+ if(req)
+ Curl_http_req_free(req);
return result;
}
-static CURLcode send_CONNECT(struct Curl_easy *data,
- struct connectdata *conn,
+static CURLcode send_CONNECT(struct Curl_cfilter *cf,
+ struct Curl_easy *data,
struct h1_tunnel_state *ts,
bool *done)
{
- struct SingleRequest *k = &data->req;
- struct HTTP *http = &ts->CONNECT;
+ char *buf = Curl_dyn_ptr(&ts->request_data);
+ size_t request_len = Curl_dyn_len(&ts->request_data);
+ size_t blen = request_len;
CURLcode result = CURLE_OK;
+ ssize_t nwritten;
- if(http->sending != HTTPSEND_REQUEST)
- goto out;
+ if(blen <= ts->nsent)
+ goto out; /* we are done */
- if(!ts->nsend) {
- size_t fillcount;
- k->upload_fromhere = data->state.ulbuf;
- result = Curl_fillreadbuffer(data, data->set.upload_buffer_size,
- &fillcount);
- if(result)
- goto out;
- ts->nsend = fillcount;
- }
- if(ts->nsend) {
- ssize_t bytes_written;
- /* write to socket (send away data) */
- result = Curl_write(data,
- conn->writesockfd, /* socket to send to */
- k->upload_fromhere, /* buffer pointer */
- ts->nsend, /* buffer size */
- &bytes_written); /* actually sent */
- if(result)
- goto out;
- /* send to debug callback! */
- Curl_debug(data, CURLINFO_HEADER_OUT,
- k->upload_fromhere, bytes_written);
+ blen -= ts->nsent;
+ buf += ts->nsent;
- ts->nsend -= bytes_written;
- k->upload_fromhere += bytes_written;
+ nwritten = cf->next->cft->do_send(cf->next, data, buf, blen, &result);
+ if(nwritten < 0) {
+ if(result == CURLE_AGAIN) {
+ result = CURLE_OK;
+ }
+ goto out;
}
- if(!ts->nsend)
- http->sending = HTTPSEND_NADA;
+
+ DEBUGASSERT(blen >= (size_t)nwritten);
+ ts->nsent += (size_t)nwritten;
+ Curl_debug(data, CURLINFO_HEADER_OUT, buf, (size_t)nwritten);
out:
if(result)
failf(data, "Failed sending CONNECT to proxy");
- *done = (http->sending != HTTPSEND_REQUEST);
+ *done = (!result && (ts->nsent >= request_len));
return result;
}
@@ -491,7 +382,7 @@ static CURLcode recv_CONNECT_resp(struct Curl_cfilter *cf,
error = SELECT_OK;
*done = FALSE;
- if(!Curl_conn_data_pending(data, ts->sockindex))
+ if(!Curl_conn_data_pending(data, cf->sockindex))
return CURLE_OK;
while(ts->keepon) {
@@ -579,7 +470,6 @@ static CURLcode recv_CONNECT_resp(struct Curl_cfilter *cf,
if(!data->set.suppress_connect_headers) {
/* send the header to the callback */
int writetype = CLIENTWRITE_HEADER | CLIENTWRITE_CONNECT |
- (data->set.include_header ? CLIENTWRITE_BODY : 0) |
(ts->headerlines == 1 ? CLIENTWRITE_STATUS : 0);
result = Curl_client_write(data, writetype, linep, perline);
@@ -670,6 +560,41 @@ static CURLcode recv_CONNECT_resp(struct Curl_cfilter *cf,
}
#else /* USE_HYPER */
+
+static CURLcode CONNECT_host(struct Curl_cfilter *cf,
+ struct Curl_easy *data,
+ char **pauthority,
+ char **phost_header)
+{
+ const char *hostname;
+ int port;
+ bool ipv6_ip;
+ CURLcode result;
+ char *authority; /* for CONNECT, the destination host + port */
+ char *host_header = NULL; /* Host: authority */
+
+ result = Curl_http_proxy_get_destination(cf, &hostname, &port, &ipv6_ip);
+ if(result)
+ return result;
+
+ authority = aprintf("%s%s%s:%d", ipv6_ip?"[":"", hostname, ipv6_ip?"]":"",
+ port);
+ if(!authority)
+ return CURLE_OUT_OF_MEMORY;
+
+ /* If user is not overriding the Host header later */
+ if(!Curl_checkProxyheaders(data, cf->conn, STRCONST("Host"))) {
+ host_header = aprintf("Host: %s\r\n", authority);
+ if(!host_header) {
+ free(authority);
+ return CURLE_OUT_OF_MEMORY;
+ }
+ }
+ *pauthority = authority;
+ *phost_header = host_header;
+ return CURLE_OK;
+}
+
/* The Hyper version of CONNECT */
static CURLcode start_CONNECT(struct Curl_cfilter *cf,
struct Curl_easy *data,
@@ -686,9 +611,10 @@ static CURLcode start_CONNECT(struct Curl_cfilter *cf,
hyper_task *task = NULL; /* for the handshake */
hyper_clientconn *client = NULL;
hyper_task *sendtask = NULL; /* for the send */
- char *hostheader = NULL; /* for CONNECT */
- char *host = NULL; /* Host: */
+ char *authority = NULL; /* for CONNECT */
+ char *host_header = NULL; /* Host: */
CURLcode result = CURLE_OUT_OF_MEMORY;
+ (void)ts;
io = hyper_io_new();
if(!io) {
@@ -766,27 +692,25 @@ static CURLcode start_CONNECT(struct Curl_cfilter *cf,
goto error;
}
- infof(data, "Establish HTTP proxy tunnel to %s:%d",
- ts->hostname, ts->remote_port);
-
/* This only happens if we've looped here due to authentication
reasons, and we don't really use the newly cloned URL here
then. Just free() it. */
Curl_safefree(data->req.newurl);
- result = CONNECT_host(data, conn, ts->hostname, ts->remote_port,
- &hostheader, &host);
+ result = CONNECT_host(cf, data, &authority, &host_header);
if(result)
goto error;
- if(hyper_request_set_uri(req, (uint8_t *)hostheader,
- strlen(hostheader))) {
+ infof(data, "Establish HTTP proxy tunnel to %s", authority);
+
+ if(hyper_request_set_uri(req, (uint8_t *)authority,
+ strlen(authority))) {
failf(data, "error setting path");
result = CURLE_OUT_OF_MEMORY;
goto error;
}
if(data->set.verbose) {
- char *se = aprintf("CONNECT %s HTTP/1.1\r\n", hostheader);
+ char *se = aprintf("CONNECT %s HTTP/1.1\r\n", authority);
if(!se) {
result = CURLE_OUT_OF_MEMORY;
goto error;
@@ -796,10 +720,10 @@ static CURLcode start_CONNECT(struct Curl_cfilter *cf,
}
/* Setup the proxy-authorization header, if any */
result = Curl_http_output_auth(data, conn, "CONNECT", HTTPREQ_GET,
- hostheader, TRUE);
+ authority, TRUE);
if(result)
goto error;
- Curl_safefree(hostheader);
+ Curl_safefree(authority);
/* default is 1.1 */
if((conn->http_proxy.proxytype == CURLPROXY_HTTP_1_0) &&
@@ -816,11 +740,11 @@ static CURLcode start_CONNECT(struct Curl_cfilter *cf,
result = CURLE_OUT_OF_MEMORY;
goto error;
}
- if(host) {
- result = Curl_hyper_header(data, headers, host);
+ if(host_header) {
+ result = Curl_hyper_header(data, headers, host_header);
if(result)
goto error;
- Curl_safefree(host);
+ Curl_safefree(host_header);
}
if(data->state.aptr.proxyuserpwd) {
@@ -874,8 +798,8 @@ static CURLcode start_CONNECT(struct Curl_cfilter *cf,
client = NULL;
error:
- free(host);
- free(hostheader);
+ free(host_header);
+ free(authority);
if(io)
hyper_io_free(io);
if(options)
@@ -890,12 +814,13 @@ error:
return result;
}
-static CURLcode send_CONNECT(struct Curl_easy *data,
- struct connectdata *conn,
+static CURLcode send_CONNECT(struct Curl_cfilter *cf,
+ struct Curl_easy *data,
struct h1_tunnel_state *ts,
bool *done)
{
struct hyptransfer *h = &data->hyp;
+ struct connectdata *conn = cf->conn;
hyper_task *task = NULL;
hyper_error *hypererr = NULL;
CURLcode result = CURLE_OK;
@@ -995,7 +920,7 @@ static CURLcode H1_CONNECT(struct Curl_cfilter *cf,
case H1_TUNNEL_CONNECT:
/* see that the request is completely sent */
CURL_TRC_CF(data, cf, "CONNECT send");
- result = send_CONNECT(data, cf->conn, ts, &done);
+ result = send_CONNECT(cf, data, ts, &done);
if(result || !done)
goto out;
h1_tunnel_go_state(cf, ts, H1_TUNNEL_RECEIVE, data);
@@ -1090,7 +1015,7 @@ static CURLcode cf_h1_proxy_connect(struct Curl_cfilter *cf,
*done = FALSE;
if(!ts) {
- result = tunnel_init(&ts, data, cf->conn, cf->sockindex);
+ result = tunnel_init(cf, data, &ts);
if(result)
return result;
cf->ctx = ts;
diff --git a/Utilities/cmcurl/lib/cf-h2-proxy.c b/Utilities/cmcurl/lib/cf-h2-proxy.c
index a3feefc..dbc895d 100644
--- a/Utilities/cmcurl/lib/cf-h2-proxy.c
+++ b/Utilities/cmcurl/lib/cf-h2-proxy.c
@@ -84,7 +84,8 @@ static CURLcode tunnel_stream_init(struct Curl_cfilter *cf,
{
const char *hostname;
int port;
- bool ipv6_ip = cf->conn->bits.ipv6_ip;
+ bool ipv6_ip;
+ CURLcode result;
ts->state = H2_TUNNEL_INIT;
ts->stream_id = -1;
@@ -92,22 +93,9 @@ static CURLcode tunnel_stream_init(struct Curl_cfilter *cf,
BUFQ_OPT_SOFT_LIMIT);
Curl_bufq_init(&ts->sendbuf, PROXY_H2_CHUNK_SIZE, H2_TUNNEL_SEND_CHUNKS);
- if(cf->conn->bits.conn_to_host)
- hostname = cf->conn->conn_to_host.name;
- else if(cf->sockindex == SECONDARYSOCKET)
- hostname = cf->conn->secondaryhostname;
- else
- hostname = cf->conn->host.name;
-
- if(cf->sockindex == SECONDARYSOCKET)
- port = cf->conn->secondary_port;
- else if(cf->conn->bits.conn_to_port)
- port = cf->conn->conn_to_port;
- else
- port = cf->conn->remote_port;
-
- if(hostname != cf->conn->host.name)
- ipv6_ip = (strchr(hostname, ':') != NULL);
+ result = Curl_http_proxy_get_destination(cf, &hostname, &port, &ipv6_ip);
+ if(result)
+ return result;
ts->authority = /* host:port with IPv6 support */
aprintf("%s%s%s:%d", ipv6_ip?"[":"", hostname, ipv6_ip?"]":"", port);
@@ -233,7 +221,7 @@ static void drain_tunnel(struct Curl_cfilter *cf,
bits = CURL_CSELECT_IN;
if(!tunnel->closed && !tunnel->reset && tunnel->upload_blocked_len)
bits |= CURL_CSELECT_OUT;
- if(data->state.dselect_bits != bits || 1) {
+ if(data->state.dselect_bits != bits) {
CURL_TRC_CF(data, cf, "[%d] DRAIN dselect_bits=%x",
tunnel->stream_id, bits);
data->state.dselect_bits = bits;
@@ -309,8 +297,9 @@ static int proxy_h2_on_frame_recv(nghttp2_session *session,
const nghttp2_frame *frame,
void *userp);
#ifndef CURL_DISABLE_VERBOSE_STRINGS
-static int on_frame_send(nghttp2_session *session, const nghttp2_frame *frame,
- void *userp);
+static int proxy_h2_on_frame_send(nghttp2_session *session,
+ const nghttp2_frame *frame,
+ void *userp);
#endif
static int proxy_h2_on_stream_close(nghttp2_session *session,
int32_t stream_id,
@@ -355,7 +344,8 @@ static CURLcode cf_h2_proxy_ctx_init(struct Curl_cfilter *cf,
nghttp2_session_callbacks_set_on_frame_recv_callback(
cbs, proxy_h2_on_frame_recv);
#ifndef CURL_DISABLE_VERBOSE_STRINGS
- nghttp2_session_callbacks_set_on_frame_send_callback(cbs, on_frame_send);
+ nghttp2_session_callbacks_set_on_frame_send_callback(cbs,
+ proxy_h2_on_frame_send);
#endif
nghttp2_session_callbacks_set_on_data_chunk_recv_callback(
cbs, tunnel_recv_callback);
@@ -575,7 +565,8 @@ static ssize_t on_session_send(nghttp2_session *h2,
}
#ifndef CURL_DISABLE_VERBOSE_STRINGS
-static int fr_print(const nghttp2_frame *frame, char *buffer, size_t blen)
+static int proxy_h2_fr_print(const nghttp2_frame *frame,
+ char *buffer, size_t blen)
{
switch(frame->hd.type) {
case NGHTTP2_DATA: {
@@ -646,8 +637,9 @@ static int fr_print(const nghttp2_frame *frame, char *buffer, size_t blen)
}
}
-static int on_frame_send(nghttp2_session *session, const nghttp2_frame *frame,
- void *userp)
+static int proxy_h2_on_frame_send(nghttp2_session *session,
+ const nghttp2_frame *frame,
+ void *userp)
{
struct Curl_cfilter *cf = userp;
struct Curl_easy *data = CF_DATA_CURRENT(cf);
@@ -657,7 +649,7 @@ static int on_frame_send(nghttp2_session *session, const nghttp2_frame *frame,
if(data && Curl_trc_cf_is_verbose(cf, data)) {
char buffer[256];
int len;
- len = fr_print(frame, buffer, sizeof(buffer)-1);
+ len = proxy_h2_fr_print(frame, buffer, sizeof(buffer)-1);
buffer[len] = 0;
CURL_TRC_CF(data, cf, "[%d] -> %s", frame->hd.stream_id, buffer);
}
@@ -680,7 +672,7 @@ static int proxy_h2_on_frame_recv(nghttp2_session *session,
if(Curl_trc_cf_is_verbose(cf, data)) {
char buffer[256];
int len;
- len = fr_print(frame, buffer, sizeof(buffer)-1);
+ len = proxy_h2_fr_print(frame, buffer, sizeof(buffer)-1);
buffer[len] = 0;
CURL_TRC_CF(data, cf, "[%d] <- %s",frame->hd.stream_id, buffer);
}
@@ -980,38 +972,11 @@ static CURLcode submit_CONNECT(struct Curl_cfilter *cf,
CURLcode result;
struct httpreq *req = NULL;
- infof(data, "Establish HTTP/2 proxy tunnel to %s", ts->authority);
-
- result = Curl_http_req_make(&req, "CONNECT", sizeof("CONNECT")-1,
- NULL, 0, ts->authority, strlen(ts->authority),
- NULL, 0);
+ result = Curl_http_proxy_create_CONNECT(&req, cf, data, 2);
if(result)
goto out;
- /* Setup the proxy-authorization header, if any */
- result = Curl_http_output_auth(data, cf->conn, req->method, HTTPREQ_GET,
- req->authority, TRUE);
- if(result)
- goto out;
-
- if(data->state.aptr.proxyuserpwd) {
- result = Curl_dynhds_h1_cadd_line(&req->headers,
- data->state.aptr.proxyuserpwd);
- if(result)
- goto out;
- }
-
- if(!Curl_checkProxyheaders(data, cf->conn, STRCONST("User-Agent"))
- && data->set.str[STRING_USERAGENT]) {
- result = Curl_dynhds_cadd(&req->headers, "User-Agent",
- data->set.str[STRING_USERAGENT]);
- if(result)
- goto out;
- }
-
- result = Curl_dynhds_add_custom(data, TRUE, &req->headers);
- if(result)
- goto out;
+ infof(data, "Establish HTTP/2 proxy tunnel to %s", req->authority);
result = proxy_h2_submit(&ts->stream_id, cf, data, ctx->h2, req,
NULL, ts, tunnel_send_callback, cf);
@@ -1058,7 +1023,7 @@ static CURLcode inspect_response(struct Curl_cfilter *cf,
if(result)
return result;
if(data->req.newurl) {
- /* Inidicator that we should try again */
+ /* Indicator that we should try again */
Curl_safefree(data->req.newurl);
h2_tunnel_go_state(cf, ts, H2_TUNNEL_INIT, data);
return CURLE_OK;
@@ -1195,6 +1160,8 @@ static void cf_h2_proxy_close(struct Curl_cfilter *cf, struct Curl_easy *data)
cf_h2_proxy_ctx_clear(ctx);
CF_DATA_RESTORE(cf, save);
}
+ if(cf->next)
+ cf->next->cft->do_close(cf->next, data);
}
static void cf_h2_proxy_destroy(struct Curl_cfilter *cf,
diff --git a/Utilities/cmcurl/lib/cf-socket.c b/Utilities/cmcurl/lib/cf-socket.c
index effe6e6..ce3f9e9 100644
--- a/Utilities/cmcurl/lib/cf-socket.c
+++ b/Utilities/cmcurl/lib/cf-socket.c
@@ -781,6 +781,8 @@ struct cf_socket_ctx {
#ifdef DEBUGBUILD
int wblock_percent; /* percent of writes doing EAGAIN */
int wpartial_percent; /* percent of bytes written in send */
+ int rblock_percent; /* percent of reads doing EAGAIN */
+ size_t recv_max; /* max enforced read size */
#endif
BIT(got_first_byte); /* if first byte was received */
BIT(accepted); /* socket was accepted, not connected */
@@ -811,6 +813,18 @@ static void cf_socket_ctx_init(struct cf_socket_ctx *ctx,
if(l >= 0 && l <= 100)
ctx->wpartial_percent = (int)l;
}
+ p = getenv("CURL_DBG_SOCK_RBLOCK");
+ if(p) {
+ long l = strtol(p, NULL, 10);
+ if(l >= 0 && l <= 100)
+ ctx->rblock_percent = (int)l;
+ }
+ p = getenv("CURL_DBG_SOCK_RMAX");
+ if(p) {
+ long l = strtol(p, NULL, 10);
+ if(l >= 0)
+ ctx->recv_max = (size_t)l;
+ }
}
#endif
}
@@ -1358,6 +1372,27 @@ static ssize_t cf_socket_recv(struct Curl_cfilter *cf, struct Curl_easy *data,
fdsave = cf->conn->sock[cf->sockindex];
cf->conn->sock[cf->sockindex] = ctx->sock;
+#ifdef DEBUGBUILD
+ /* simulate network blocking/partial reads */
+ if(cf->cft != &Curl_cft_udp && ctx->rblock_percent > 0) {
+ unsigned char c;
+ Curl_rand(data, &c, 1);
+ if(c >= ((100-ctx->rblock_percent)*256/100)) {
+ CURL_TRC_CF(data, cf, "recv(len=%zu) SIMULATE EWOULDBLOCK", len);
+ *err = CURLE_AGAIN;
+ nread = -1;
+ cf->conn->sock[cf->sockindex] = fdsave;
+ return nread;
+ }
+ }
+ if(cf->cft != &Curl_cft_udp && ctx->recv_max && ctx->recv_max < len) {
+ size_t orig_len = len;
+ len = ctx->recv_max;
+ CURL_TRC_CF(data, cf, "recv(len=%zu) SIMULATE max read of %zu bytes",
+ orig_len, len);
+ }
+#endif
+
if(ctx->buffer_recv && !Curl_bufq_is_empty(&ctx->recvbuf)) {
CURL_TRC_CF(data, cf, "recv from buffer");
nread = Curl_bufq_read(&ctx->recvbuf, (unsigned char *)buf, len, err);
diff --git a/Utilities/cmcurl/lib/conncache.c b/Utilities/cmcurl/lib/conncache.c
index a21409c..93d8768 100644
--- a/Utilities/cmcurl/lib/conncache.c
+++ b/Utilities/cmcurl/lib/conncache.c
@@ -107,6 +107,7 @@ int Curl_conncache_init(struct conncache *connc, int size)
connc->closure_handle = curl_easy_init();
if(!connc->closure_handle)
return 1; /* bad */
+ connc->closure_handle->internal = true;
Curl_hash_init(&connc->hash, size, Curl_hash_str,
Curl_str_key_compare, free_bundle_hash_entry);
diff --git a/Utilities/cmcurl/lib/connect.c b/Utilities/cmcurl/lib/connect.c
index 033fb7b..c7ba3e2 100644
--- a/Utilities/cmcurl/lib/connect.c
+++ b/Utilities/cmcurl/lib/connect.c
@@ -634,6 +634,7 @@ evaluate:
/* next attempt was started */
CURL_TRC_CF(data, cf, "%s trying next", baller->name);
++ongoing;
+ Curl_expire(data, 0, EXPIRE_RUN_NOW);
}
}
}
@@ -646,7 +647,7 @@ evaluate:
/* Nothing connected, check the time before we might
* start new ballers or return ok. */
if((ongoing || not_started) && Curl_timeleft(data, &now, TRUE) < 0) {
- failf(data, "Connection timeout after %ld ms",
+ failf(data, "Connection timeout after %" CURL_FORMAT_CURL_OFF_T " ms",
Curl_timediff(now, data->progress.t_startsingle));
return CURLE_OPERATION_TIMEDOUT;
}
@@ -823,11 +824,10 @@ static CURLcode start_connect(struct Curl_cfilter *cf,
CURL_TRC_CF(data, cf, "created %s (timeout %"
CURL_FORMAT_TIMEDIFF_T "ms)",
ctx->baller[1]->name, ctx->baller[1]->timeoutms);
+ Curl_expire(data, data->set.happy_eyeballs_timeout,
+ EXPIRE_HAPPY_EYEBALLS);
}
- Curl_expire(data, data->set.happy_eyeballs_timeout,
- EXPIRE_HAPPY_EYEBALLS);
-
return CURLE_OK;
}
diff --git a/Utilities/cmcurl/lib/content_encoding.c b/Utilities/cmcurl/lib/content_encoding.c
index 5b2fc6f..ec4750e 100644
--- a/Utilities/cmcurl/lib/content_encoding.c
+++ b/Utilities/cmcurl/lib/content_encoding.c
@@ -280,9 +280,6 @@ static CURLcode deflate_init_writer(struct Curl_easy *data,
struct zlib_writer *zp = (struct zlib_writer *) writer;
z_stream *z = &zp->z; /* zlib state structure */
- if(!writer->downstream)
- return CURLE_WRITE_ERROR;
-
/* Initialize zlib */
z->zalloc = (alloc_func) zalloc_cb;
z->zfree = (free_func) zfree_cb;
@@ -337,9 +334,6 @@ static CURLcode gzip_init_writer(struct Curl_easy *data,
struct zlib_writer *zp = (struct zlib_writer *) writer;
z_stream *z = &zp->z; /* zlib state structure */
- if(!writer->downstream)
- return CURLE_WRITE_ERROR;
-
/* Initialize zlib */
z->zalloc = (alloc_func) zalloc_cb;
z->zfree = (free_func) zfree_cb;
@@ -647,9 +641,6 @@ static CURLcode brotli_init_writer(struct Curl_easy *data,
struct brotli_writer *bp = (struct brotli_writer *) writer;
(void) data;
- if(!writer->downstream)
- return CURLE_WRITE_ERROR;
-
bp->br = BrotliDecoderCreateInstance(NULL, NULL, NULL);
return bp->br? CURLE_OK: CURLE_OUT_OF_MEMORY;
}
@@ -741,9 +732,6 @@ static CURLcode zstd_init_writer(struct Curl_easy *data,
(void)data;
- if(!writer->downstream)
- return CURLE_WRITE_ERROR;
-
zp->zds = ZSTD_createDStream();
zp->decomp = NULL;
return zp->zds ? CURLE_OK : CURLE_OUT_OF_MEMORY;
@@ -822,8 +810,9 @@ static const struct content_encoding zstd_encoding = {
static CURLcode identity_init_writer(struct Curl_easy *data,
struct contenc_writer *writer)
{
- (void) data;
- return writer->downstream? CURLE_OK: CURLE_WRITE_ERROR;
+ (void)data;
+ (void)writer;
+ return CURLE_OK;
}
static CURLcode identity_unencode_write(struct Curl_easy *data,
@@ -903,51 +892,13 @@ char *Curl_all_content_encodings(void)
}
-/* Real client writer: no downstream. */
-static CURLcode client_init_writer(struct Curl_easy *data,
- struct contenc_writer *writer)
-{
- (void) data;
- return writer->downstream? CURLE_WRITE_ERROR: CURLE_OK;
-}
-
-static CURLcode client_unencode_write(struct Curl_easy *data,
- struct contenc_writer *writer,
- const char *buf, size_t nbytes)
-{
- struct SingleRequest *k = &data->req;
-
- (void) writer;
-
- if(!nbytes || k->ignorebody)
- return CURLE_OK;
-
- return Curl_client_write(data, CLIENTWRITE_BODY, (char *) buf, nbytes);
-}
-
-static void client_close_writer(struct Curl_easy *data,
- struct contenc_writer *writer)
-{
- (void) data;
- (void) writer;
-}
-
-static const struct content_encoding client_encoding = {
- NULL,
- NULL,
- client_init_writer,
- client_unencode_write,
- client_close_writer,
- sizeof(struct contenc_writer)
-};
-
-
/* Deferred error dummy writer. */
static CURLcode error_init_writer(struct Curl_easy *data,
struct contenc_writer *writer)
{
- (void) data;
- return writer->downstream? CURLE_OK: CURLE_WRITE_ERROR;
+ (void)data;
+ (void)writer;
+ return CURLE_OK;
}
static CURLcode error_unencode_write(struct Curl_easy *data,
@@ -984,31 +935,6 @@ static const struct content_encoding error_encoding = {
sizeof(struct contenc_writer)
};
-/* Create an unencoding writer stage using the given handler. */
-static struct contenc_writer *
-new_unencoding_writer(struct Curl_easy *data,
- const struct content_encoding *handler,
- struct contenc_writer *downstream,
- int order)
-{
- struct contenc_writer *writer;
-
- DEBUGASSERT(handler->writersize >= sizeof(struct contenc_writer));
- writer = (struct contenc_writer *) calloc(1, handler->writersize);
-
- if(writer) {
- writer->handler = handler;
- writer->downstream = downstream;
- writer->order = order;
- if(handler->init_writer(data, writer)) {
- free(writer);
- writer = NULL;
- }
- }
-
- return writer;
-}
-
/* Write data using an unencoding writer stack. "nbytes" is not
allowed to be 0. */
CURLcode Curl_unencode_write(struct Curl_easy *data,
@@ -1017,23 +943,11 @@ CURLcode Curl_unencode_write(struct Curl_easy *data,
{
if(!nbytes)
return CURLE_OK;
+ if(!writer)
+ return CURLE_WRITE_ERROR;
return writer->handler->unencode_write(data, writer, buf, nbytes);
}
-/* Close and clean-up the connection's writer stack. */
-void Curl_unencode_cleanup(struct Curl_easy *data)
-{
- struct SingleRequest *k = &data->req;
- struct contenc_writer *writer = k->writer_stack;
-
- while(writer) {
- k->writer_stack = writer->downstream;
- writer->handler->close_writer(data, writer);
- free(writer);
- writer = k->writer_stack;
- }
-}
-
/* Find the content encoding by name. */
static const struct content_encoding *find_encoding(const char *name,
size_t len)
@@ -1049,9 +963,6 @@ static const struct content_encoding *find_encoding(const char *name,
return NULL;
}
-/* allow no more than 5 "chained" compression steps */
-#define MAX_ENCODE_STACK 5
-
/* Set-up the unencoding stack from the Content-Encoding header value.
* See RFC 7231 section 3.1.2.2. */
CURLcode Curl_build_unencoding_stack(struct Curl_easy *data,
@@ -1059,6 +970,7 @@ CURLcode Curl_build_unencoding_stack(struct Curl_easy *data,
{
struct SingleRequest *k = &data->req;
unsigned int order = is_transfer? 2: 1;
+ CURLcode result;
do {
const char *name;
@@ -1085,41 +997,19 @@ CURLcode Curl_build_unencoding_stack(struct Curl_easy *data,
if(is_transfer && !data->set.http_transfer_encoding)
/* not requested, ignore */
return CURLE_OK;
- encoding = find_encoding(name, namelen);
-
- if(!k->writer_stack) {
- k->writer_stack = new_unencoding_writer(data, &client_encoding,
- NULL, 0);
-
- if(!k->writer_stack)
- return CURLE_OUT_OF_MEMORY;
- }
+ encoding = find_encoding(name, namelen);
if(!encoding)
encoding = &error_encoding; /* Defer error at stack use. */
- if(k->writer_stack_depth++ >= MAX_ENCODE_STACK) {
- failf(data, "Reject response due to more than %u content encodings",
- MAX_ENCODE_STACK);
- return CURLE_BAD_CONTENT_ENCODING;
- }
- /* Stack the unencoding stage. */
- if(order >= k->writer_stack->order) {
- writer = new_unencoding_writer(data, encoding,
- k->writer_stack, order);
- if(!writer)
- return CURLE_OUT_OF_MEMORY;
- k->writer_stack = writer;
- }
- else {
- struct contenc_writer *w = k->writer_stack;
- while(w->downstream && order < w->downstream->order)
- w = w->downstream;
- writer = new_unencoding_writer(data, encoding,
- w->downstream, order);
- if(!writer)
- return CURLE_OUT_OF_MEMORY;
- w->downstream = writer;
+ result = Curl_client_create_writer(&writer, data, encoding, order);
+ if(result)
+ return result;
+
+ result = Curl_client_add_writer(data, writer);
+ if(result) {
+ Curl_client_free_writer(data, writer);
+ return result;
}
}
} while(*enclist);
@@ -1149,11 +1039,6 @@ CURLcode Curl_unencode_write(struct Curl_easy *data,
return CURLE_NOT_BUILT_IN;
}
-void Curl_unencode_cleanup(struct Curl_easy *data)
-{
- (void) data;
-}
-
char *Curl_all_content_encodings(void)
{
return strdup(CONTENT_ENCODING_DEFAULT); /* Satisfy caller. */
diff --git a/Utilities/cmcurl/lib/content_encoding.h b/Utilities/cmcurl/lib/content_encoding.h
index 56e7f97..ef7930c 100644
--- a/Utilities/cmcurl/lib/content_encoding.h
+++ b/Utilities/cmcurl/lib/content_encoding.h
@@ -25,26 +25,9 @@
***************************************************************************/
#include "curl_setup.h"
-struct contenc_writer {
- const struct content_encoding *handler; /* Encoding handler. */
- struct contenc_writer *downstream; /* Downstream writer. */
- unsigned int order; /* Ordering within writer stack. */
-};
-
-/* Content encoding writer. */
-struct content_encoding {
- const char *name; /* Encoding name. */
- const char *alias; /* Encoding name alias. */
- CURLcode (*init_writer)(struct Curl_easy *data,
- struct contenc_writer *writer);
- CURLcode (*unencode_write)(struct Curl_easy *data,
- struct contenc_writer *writer,
- const char *buf, size_t nbytes);
- void (*close_writer)(struct Curl_easy *data,
- struct contenc_writer *writer);
- size_t writersize;
-};
+struct contenc_writer;
+char *Curl_all_content_encodings(void);
CURLcode Curl_build_unencoding_stack(struct Curl_easy *data,
const char *enclist, int is_transfer);
@@ -52,6 +35,5 @@ CURLcode Curl_unencode_write(struct Curl_easy *data,
struct contenc_writer *writer,
const char *buf, size_t nbytes);
void Curl_unencode_cleanup(struct Curl_easy *data);
-char *Curl_all_content_encodings(void);
#endif /* HEADER_CURL_CONTENT_ENCODING_H */
diff --git a/Utilities/cmcurl/lib/cookie.c b/Utilities/cmcurl/lib/cookie.c
index 4345a84..af01203 100644
--- a/Utilities/cmcurl/lib/cookie.c
+++ b/Utilities/cmcurl/lib/cookie.c
@@ -112,14 +112,11 @@ static void strstore(char **str, const char *newstr, size_t len);
static void freecookie(struct Cookie *co)
{
- free(co->expirestr);
free(co->domain);
free(co->path);
free(co->spath);
free(co->name);
free(co->value);
- free(co->maxage);
- free(co->version);
free(co);
}
@@ -487,7 +484,7 @@ Curl_cookie_add(struct Curl_easy *data,
struct CookieInfo *c,
bool httpheader, /* TRUE if HTTP header-style line */
bool noexpire, /* if TRUE, skip remove_expired() */
- char *lineptr, /* first character of the line */
+ const char *lineptr, /* first character of the line */
const char *domain, /* default domain */
const char *path, /* full path used when this cookie is set,
used to get default path for the cookie
@@ -718,11 +715,7 @@ Curl_cookie_add(struct Curl_easy *data,
}
}
else if((nlen == 7) && strncasecompare("version", namep, 7)) {
- strstore(&co->version, valuep, vlen);
- if(!co->version) {
- badcookie = TRUE;
- break;
- }
+ /* just ignore */
}
else if((nlen == 7) && strncasecompare("max-age", namep, 7)) {
/*
@@ -734,17 +727,55 @@ Curl_cookie_add(struct Curl_easy *data,
* client should discard the cookie. A value of zero means the
* cookie should be discarded immediately.
*/
- strstore(&co->maxage, valuep, vlen);
- if(!co->maxage) {
- badcookie = TRUE;
+ CURLofft offt;
+ const char *maxage = valuep;
+ offt = curlx_strtoofft((*maxage == '\"')?
+ &maxage[1]:&maxage[0], NULL, 10,
+ &co->expires);
+ switch(offt) {
+ case CURL_OFFT_FLOW:
+ /* overflow, used max value */
+ co->expires = CURL_OFF_T_MAX;
+ break;
+ case CURL_OFFT_INVAL:
+ /* negative or otherwise bad, expire */
+ co->expires = 1;
+ break;
+ case CURL_OFFT_OK:
+ if(!co->expires)
+ /* already expired */
+ co->expires = 1;
+ else if(CURL_OFF_T_MAX - now < co->expires)
+ /* would overflow */
+ co->expires = CURL_OFF_T_MAX;
+ else
+ co->expires += now;
break;
}
}
else if((nlen == 7) && strncasecompare("expires", namep, 7)) {
- strstore(&co->expirestr, valuep, vlen);
- if(!co->expirestr) {
- badcookie = TRUE;
- break;
+ char date[128];
+ if(!co->expires && (vlen < sizeof(date))) {
+ /* copy the date so that it can be null terminated */
+ memcpy(date, valuep, vlen);
+ date[vlen] = 0;
+ /*
+ * Let max-age have priority.
+ *
+ * If the date cannot get parsed for whatever reason, the cookie
+ * will be treated as a session cookie
+ */
+ co->expires = Curl_getdate_capped(date);
+
+ /*
+ * Session cookies have expires set to 0 so if we get that back
+ * from the date parser let's add a second to make it a
+ * non-session cookie
+ */
+ if(co->expires == 0)
+ co->expires = 1;
+ else if(co->expires < 0)
+ co->expires = 0;
}
}
@@ -764,49 +795,6 @@ Curl_cookie_add(struct Curl_easy *data,
break;
} while(1);
- if(co->maxage) {
- CURLofft offt;
- offt = curlx_strtoofft((*co->maxage == '\"')?
- &co->maxage[1]:&co->maxage[0], NULL, 10,
- &co->expires);
- switch(offt) {
- case CURL_OFFT_FLOW:
- /* overflow, used max value */
- co->expires = CURL_OFF_T_MAX;
- break;
- case CURL_OFFT_INVAL:
- /* negative or otherwise bad, expire */
- co->expires = 1;
- break;
- case CURL_OFFT_OK:
- if(!co->expires)
- /* already expired */
- co->expires = 1;
- else if(CURL_OFF_T_MAX - now < co->expires)
- /* would overflow */
- co->expires = CURL_OFF_T_MAX;
- else
- co->expires += now;
- break;
- }
- }
- else if(co->expirestr) {
- /*
- * Note that if the date couldn't get parsed for whatever reason, the
- * cookie will be treated as a session cookie
- */
- co->expires = Curl_getdate_capped(co->expirestr);
-
- /*
- * Session cookies have expires set to 0 so if we get that back from the
- * date parser let's add a second to make it a non-session cookie
- */
- if(co->expires == 0)
- co->expires = 1;
- else if(co->expires < 0)
- co->expires = 0;
- }
-
if(!badcookie && !co->domain) {
if(domain) {
/* no domain was given in the header line, set the default */
@@ -894,7 +882,7 @@ Curl_cookie_add(struct Curl_easy *data,
if(ptr)
*ptr = 0; /* clear it */
- firstptr = strtok_r(lineptr, "\t", &tok_buf); /* tokenize it on the TAB */
+ firstptr = strtok_r((char *)lineptr, "\t", &tok_buf); /* tokenize on TAB */
/*
* Now loop through the fields and init the struct we already have
@@ -1159,9 +1147,6 @@ Curl_cookie_add(struct Curl_easy *data,
free(clist->domain);
free(clist->path);
free(clist->spath);
- free(clist->expirestr);
- free(clist->version);
- free(clist->maxage);
*clist = *co; /* then store all the new data */
@@ -1224,9 +1209,6 @@ struct CookieInfo *Curl_cookie_init(struct Curl_easy *data,
c = calloc(1, sizeof(struct CookieInfo));
if(!c)
return NULL; /* failed to get memory */
- c->filename = strdup(file?file:"none"); /* copy the name just in case */
- if(!c->filename)
- goto fail; /* failed to get memory */
/*
* Initialize the next_expiration time to signal that we don't have enough
* information yet.
@@ -1255,24 +1237,20 @@ struct CookieInfo *Curl_cookie_init(struct Curl_easy *data,
c->running = FALSE; /* this is not running, this is init */
if(fp) {
- char *lineptr;
- bool headerline;
line = malloc(MAX_COOKIE_LINE);
if(!line)
goto fail;
while(Curl_get_line(line, MAX_COOKIE_LINE, fp)) {
+ char *lineptr = line;
+ bool headerline = FALSE;
if(checkprefix("Set-Cookie:", line)) {
/* This is a cookie line, get it! */
lineptr = &line[11];
headerline = TRUE;
+ while(*lineptr && ISBLANK(*lineptr))
+ lineptr++;
}
- else {
- lineptr = line;
- headerline = FALSE;
- }
- while(*lineptr && ISBLANK(*lineptr))
- lineptr++;
Curl_cookie_add(data, c, headerline, TRUE, lineptr, NULL, NULL, TRUE);
}
@@ -1288,8 +1266,8 @@ struct CookieInfo *Curl_cookie_init(struct Curl_easy *data,
fclose(handle);
}
data->state.cookie_engine = TRUE;
- c->running = TRUE; /* now, we're running */
}
+ c->running = TRUE; /* now, we're running */
return c;
@@ -1371,14 +1349,11 @@ static struct Cookie *dup_cookie(struct Cookie *src)
{
struct Cookie *d = calloc(sizeof(struct Cookie), 1);
if(d) {
- CLONE(expirestr);
CLONE(domain);
CLONE(path);
CLONE(spath);
CLONE(name);
CLONE(value);
- CLONE(maxage);
- CLONE(version);
d->expires = src->expires;
d->tailmatch = src->tailmatch;
d->secure = src->secure;
@@ -1595,7 +1570,6 @@ void Curl_cookie_cleanup(struct CookieInfo *c)
{
if(c) {
unsigned int i;
- free(c->filename);
for(i = 0; i < COOKIE_HASH_SIZE; i++)
Curl_cookie_freelist(c->cookies[i]);
free(c); /* free the base struct as well */
diff --git a/Utilities/cmcurl/lib/cookie.h b/Utilities/cmcurl/lib/cookie.h
index b3c0063..012dd89 100644
--- a/Utilities/cmcurl/lib/cookie.h
+++ b/Utilities/cmcurl/lib/cookie.h
@@ -35,12 +35,6 @@ struct Cookie {
char *spath; /* sanitized cookie path */
char *domain; /* domain = <this> */
curl_off_t expires; /* expires = <this> */
- char *expirestr; /* the plain text version */
-
- /* RFC 2109 keywords. Version=1 means 2109-compliant cookie sending */
- char *version; /* Version = <value> */
- char *maxage; /* Max-Age = <value> */
-
bool tailmatch; /* whether we do tail-matching of the domain name */
bool secure; /* whether the 'secure' keyword was used */
bool livecookie; /* updated from a server, not a stored file */
@@ -56,17 +50,16 @@ struct Cookie {
#define COOKIE_PREFIX__SECURE (1<<0)
#define COOKIE_PREFIX__HOST (1<<1)
-#define COOKIE_HASH_SIZE 256
+#define COOKIE_HASH_SIZE 63
struct CookieInfo {
/* linked list of cookies we know of */
struct Cookie *cookies[COOKIE_HASH_SIZE];
- char *filename; /* file we read from/write to */
- long numcookies; /* number of cookies in the "jar" */
+ curl_off_t next_expiration; /* the next time at which expiration happens */
+ int numcookies; /* number of cookies in the "jar" */
+ int lastct; /* last creation-time used in the jar */
bool running; /* state info, for cookie adding information */
bool newsession; /* new session, discard session cookies on load */
- int lastct; /* last creation-time used in the jar */
- curl_off_t next_expiration; /* the next time at which expiration happens */
};
/* The maximum sizes we accept for cookies. RFC 6265 section 6.1 says
@@ -75,7 +68,6 @@ struct CookieInfo {
- At least 4096 bytes per cookie (as measured by the sum of the length of
the cookie's name, value, and attributes).
-
In the 6265bis draft document section 5.4 it is phrased even stronger: "If
the sum of the lengths of the name string and the value string is more than
4096 octets, abort these steps and ignore the set-cookie-string entirely."
@@ -116,7 +108,7 @@ struct Curl_easy;
struct Cookie *Curl_cookie_add(struct Curl_easy *data,
struct CookieInfo *c, bool header,
- bool noexpiry, char *lineptr,
+ bool noexpiry, const char *lineptr,
const char *domain, const char *path,
bool secure);
diff --git a/Utilities/cmcurl/lib/curl_config.h.cmake b/Utilities/cmcurl/lib/curl_config.h.cmake
index c225eef..d4bb274 100644
--- a/Utilities/cmcurl/lib/curl_config.h.cmake
+++ b/Utilities/cmcurl/lib/curl_config.h.cmake
@@ -152,18 +152,21 @@
/* Define to 1 if you have the alarm function. */
#cmakedefine HAVE_ALARM 1
+/* Define to 1 if you have the arc4random function. */
+#cmakedefine HAVE_ARC4RANDOM 1
+
/* Define to 1 if you have the <arpa/inet.h> header file. */
#cmakedefine HAVE_ARPA_INET_H 1
-/* Define to 1 if you have the <arpa/tftp.h> header file. */
-#cmakedefine HAVE_ARPA_TFTP_H 1
-
/* Define to 1 if you have _Atomic support. */
#cmakedefine HAVE_ATOMIC 1
/* Define to 1 if you have the `fchmod' function. */
#cmakedefine HAVE_FCHMOD 1
+/* Define to 1 if you have the `fnmatch' function. */
+#cmakedefine HAVE_FNMATCH 1
+
/* Define to 1 if you have the `basename' function. */
#cmakedefine HAVE_BASENAME 1
@@ -176,6 +179,10 @@
/* Define to 1 if you have the clock_gettime function and monotonic timer. */
#cmakedefine HAVE_CLOCK_GETTIME_MONOTONIC 1
+/* Define to 1 if you have the clock_gettime function and raw monotonic timer.
+ */
+#cmakedefine HAVE_CLOCK_GETTIME_MONOTONIC_RAW 1
+
/* Define to 1 if you have the `closesocket' function. */
#cmakedefine HAVE_CLOSESOCKET 1
@@ -191,6 +198,12 @@
/* Define to 1 if you have the freeaddrinfo function. */
#cmakedefine HAVE_FREEADDRINFO 1
+/* Define to 1 if you have the fseeko function. */
+#cmakedefine HAVE_FSEEKO 1
+
+/* Define to 1 if you have the _fseeki64 function. */
+#cmakedefine HAVE__FSEEKI64 1
+
/* Define to 1 if you have the ftruncate function. */
#cmakedefine HAVE_FTRUNCATE 1
@@ -227,9 +240,6 @@
/* Define to 1 if you have the `getpass_r' function. */
#cmakedefine HAVE_GETPASS_R 1
-/* Define to 1 if you have the `getppid' function. */
-#cmakedefine HAVE_GETPPID 1
-
/* Define to 1 if you have the `getpeername' function. */
#cmakedefine HAVE_GETPEERNAME 1
@@ -368,6 +378,9 @@
# define HAVE_LONGLONG 1
#endif
+/* Define to 1 if you have the 'suseconds_t' data type. */
+#cmakedefine HAVE_SUSECONDS_T 1
+
/* Define to 1 if you have the MSG_NOSIGNAL flag. */
#cmakedefine HAVE_MSG_NOSIGNAL 1
@@ -380,6 +393,9 @@
/* Define to 1 if you have the <netinet/tcp.h> header file. */
#cmakedefine HAVE_NETINET_TCP_H 1
+/* Define to 1 if you have the <netinet/udp.h> header file. */
+#cmakedefine HAVE_NETINET_UDP_H 1
+
/* Define to 1 if you have the <linux/tcp.h> header file. */
#cmakedefine HAVE_LINUX_TCP_H 1
@@ -416,9 +432,15 @@
/* Define to 1 if you have the select function. */
#cmakedefine HAVE_SELECT 1
+/* Define to 1 if you have the sched_yield function. */
+#cmakedefine HAVE_SCHED_YIELD 1
+
/* Define to 1 if you have the send function. */
#cmakedefine HAVE_SEND 1
+/* Define to 1 if you have the sendmsg function. */
+#cmakedefine HAVE_SENDMSG 1
+
/* Define to 1 if you have the 'fsetxattr' function. */
#cmakedefine HAVE_FSETXATTR 1
@@ -428,9 +450,6 @@
/* fsetxattr() takes 6 args */
#cmakedefine HAVE_FSETXATTR_6 1
-/* Define to 1 if you have the <setjmp.h> header file. */
-#cmakedefine HAVE_SETJMP_H 1
-
/* Define to 1 if you have the `setlocale' function. */
#cmakedefine HAVE_SETLOCALE 1
@@ -452,14 +471,11 @@
/* Define to 1 if you have the signal function. */
#cmakedefine HAVE_SIGNAL 1
-/* Define to 1 if you have the <signal.h> header file. */
-#cmakedefine HAVE_SIGNAL_H 1
-
/* Define to 1 if you have the sigsetjmp function or macro. */
#cmakedefine HAVE_SIGSETJMP 1
/* Define to 1 if you have the `snprintf' function. */
-#cmakedefine HAVE_SNPRINTF
+#cmakedefine HAVE_SNPRINTF 1
/* Define to 1 if struct sockaddr_in6 has the sin6_scope_id member */
#cmakedefine HAVE_SOCKADDR_IN6_SIN6_SCOPE_ID 1
@@ -479,9 +495,6 @@
/* Define to 1 if you have the <stdint.h> header file. */
#cmakedefine HAVE_STDINT_H 1
-/* Define to 1 if you have the <stdlib.h> header file. */
-#cmakedefine HAVE_STDLIB_H 1
-
/* Define to 1 if you have the strcasecmp function. */
#cmakedefine HAVE_STRCASECMP 1
@@ -500,9 +513,6 @@
/* Define to 1 if you have the <strings.h> header file. */
#cmakedefine HAVE_STRINGS_H 1
-/* Define to 1 if you have the <string.h> header file. */
-#cmakedefine HAVE_STRING_H 1
-
/* Define to 1 if you have the <stropts.h> header file. */
#cmakedefine HAVE_STROPTS_H 1
@@ -512,6 +522,9 @@
/* Define to 1 if you have the strtoll function. */
#cmakedefine HAVE_STRTOLL 1
+/* Define to 1 if you have the memrchr function. */
+#cmakedefine HAVE_MEMRCHR 1
+
/* if struct sockaddr_storage is defined */
#cmakedefine HAVE_STRUCT_SOCKADDR_STORAGE 1
@@ -521,6 +534,9 @@
/* Define to 1 if you have the <sys/filio.h> header file. */
#cmakedefine HAVE_SYS_FILIO_H 1
+/* Define to 1 if you have the <sys/wait.h> header file. */
+#cmakedefine HAVE_SYS_WAIT_H 1
+
/* Define to 1 if you have the <sys/ioctl.h> header file. */
#cmakedefine HAVE_SYS_IOCTL_H 1
@@ -563,9 +579,6 @@
/* Define to 1 if you have the <termio.h> header file. */
#cmakedefine HAVE_TERMIO_H 1
-/* Define to 1 if you have the <time.h> header file. */
-#cmakedefine HAVE_TIME_H 1
-
/* Define to 1 if you have the <unistd.h> header file. */
#cmakedefine HAVE_UNISTD_H 1
@@ -664,6 +677,9 @@ ${SIZEOF_OFF_T_CODE}
/* The size of `curl_off_t', as computed by sizeof. */
${SIZEOF_CURL_OFF_T_CODE}
+/* The size of `curl_socket_t', as computed by sizeof. */
+${SIZEOF_CURL_SOCKET_T_CODE}
+
/* The size of `size_t', as computed by sizeof. */
${SIZEOF_SIZE_T_CODE}
@@ -676,9 +692,6 @@ ${SIZEOF_TIME_T_CODE}
/* Define to 1 if you have the ANSI C header files. */
#cmakedefine STDC_HEADERS 1
-/* Define to 1 if you can safely include both <sys/time.h> and <time.h>. */
-#cmakedefine TIME_WITH_SYS_TIME 1
-
/* Define if you want to enable c-ares support */
#cmakedefine USE_ARES 1
@@ -744,7 +757,7 @@ ${SIZEOF_TIME_T_CODE}
#cmakedefine USE_MSH3 1
/* if Unix domain sockets are enabled */
-#cmakedefine USE_UNIX_SOCKETS
+#cmakedefine USE_UNIX_SOCKETS 1
/* to enable SSPI support */
#cmakedefine USE_WINDOWS_SSPI 1
@@ -808,3 +821,12 @@ ${SIZEOF_TIME_T_CODE}
/* Define to 1 to enable websocket support. */
#cmakedefine USE_WEBSOCKETS 1
+
+/* Define to 1 if OpenSSL has the SSL_CTX_set_srp_username function. */
+#cmakedefine HAVE_OPENSSL_SRP 1
+
+/* Define to 1 if GnuTLS has the gnutls_srp_verifier function. */
+#cmakedefine HAVE_GNUTLS_SRP 1
+
+/* Define to 1 to enable TLS-SRP support. */
+#cmakedefine USE_TLS_SRP 1
diff --git a/Utilities/cmcurl/lib/curl_ctype.h b/Utilities/cmcurl/lib/curl_ctype.h
index 1d1d60c..7f0d0cc 100644
--- a/Utilities/cmcurl/lib/curl_ctype.h
+++ b/Utilities/cmcurl/lib/curl_ctype.h
@@ -43,5 +43,9 @@
#define ISDIGIT(x) (((x) >= '0') && ((x) <= '9'))
#define ISBLANK(x) (((x) == ' ') || ((x) == '\t'))
#define ISSPACE(x) (ISBLANK(x) || (((x) >= 0xa) && ((x) <= 0x0d)))
+#define ISURLPUNTCS(x) (((x) == '-') || ((x) == '.') || ((x) == '_') || \
+ ((x) == '~'))
+#define ISUNRESERVED(x) (ISALNUM(x) || ISURLPUNTCS(x))
+
#endif /* HEADER_CURL_CTYPE_H */
diff --git a/Utilities/cmcurl/lib/curl_hmac.h b/Utilities/cmcurl/lib/curl_hmac.h
index 9438ca7..2ea03dd 100644
--- a/Utilities/cmcurl/lib/curl_hmac.h
+++ b/Utilities/cmcurl/lib/curl_hmac.h
@@ -24,8 +24,8 @@
*
***************************************************************************/
-#if (defined(USE_CURL_NTLM_CORE) && !defined(USE_WINDOWS_SSPI)) \
- || !defined(CURL_DISABLE_AWS)
+#if (defined(USE_CURL_NTLM_CORE) && !defined(USE_WINDOWS_SSPI)) \
+ || !defined(CURL_DISABLE_AWS) || !defined(CURL_DISABLE_DIGEST_AUTH)
#include <curl/curl.h>
diff --git a/Utilities/cmcurl/lib/curl_memrchr.h b/Utilities/cmcurl/lib/curl_memrchr.h
index a1a4ba0..45bb38c 100644
--- a/Utilities/cmcurl/lib/curl_memrchr.h
+++ b/Utilities/cmcurl/lib/curl_memrchr.h
@@ -28,9 +28,7 @@
#ifdef HAVE_MEMRCHR
-#ifdef HAVE_STRING_H
-# include <string.h>
-#endif
+#include <string.h>
#ifdef HAVE_STRINGS_H
# include <strings.h>
#endif
diff --git a/Utilities/cmcurl/lib/curl_ntlm_wb.c b/Utilities/cmcurl/lib/curl_ntlm_wb.c
index a10e2a1..aa7bea7 100644
--- a/Utilities/cmcurl/lib/curl_ntlm_wb.c
+++ b/Utilities/cmcurl/lib/curl_ntlm_wb.c
@@ -39,9 +39,7 @@
#ifdef HAVE_SYS_WAIT_H
#include <sys/wait.h>
#endif
-#ifdef HAVE_SIGNAL_H
#include <signal.h>
-#endif
#ifdef HAVE_PWD_H
#include <pwd.h>
#endif
diff --git a/Utilities/cmcurl/lib/curl_setup.h b/Utilities/cmcurl/lib/curl_setup.h
index 9d5fe99..8557cf4 100644
--- a/Utilities/cmcurl/lib/curl_setup.h
+++ b/Utilities/cmcurl/lib/curl_setup.h
@@ -28,11 +28,6 @@
#define CURL_NO_OLDIES
#endif
-/* define mingw version macros, eg __MINGW{32,64}_{MINOR,MAJOR}_VERSION */
-#ifdef __MINGW32__
-#include <_mingw.h>
-#endif
-
/*
* Disable Visual Studio warnings:
* 4127 "conditional expression is constant"
@@ -845,9 +840,6 @@ int getpwuid_r(uid_t uid, struct passwd *pwd, char *buf,
#endif
#if defined(USE_UNIX_SOCKETS) && defined(WIN32)
-# if defined(__MINGW32__) && !defined(LUP_SECURE)
- typedef u_short ADDRESS_FAMILY; /* Classic mingw, 11y+ old mingw-w64 */
-# endif
# if !defined(UNIX_PATH_MAX)
/* Replicating logic present in afunix.h
(distributed with newer Windows 10 SDK versions only) */
diff --git a/Utilities/cmcurl/lib/curl_sspi.h b/Utilities/cmcurl/lib/curl_sspi.h
index 9816d59..5af7c24 100644
--- a/Utilities/cmcurl/lib/curl_sspi.h
+++ b/Utilities/cmcurl/lib/curl_sspi.h
@@ -70,227 +70,6 @@ extern PSecurityFunctionTable s_pSecFn;
#define ISC_REQ_USE_HTTP_STYLE 0x01000000
#endif
-#ifndef ISC_RET_REPLAY_DETECT
-#define ISC_RET_REPLAY_DETECT 0x00000004
-#endif
-
-#ifndef ISC_RET_SEQUENCE_DETECT
-#define ISC_RET_SEQUENCE_DETECT 0x00000008
-#endif
-
-#ifndef ISC_RET_CONFIDENTIALITY
-#define ISC_RET_CONFIDENTIALITY 0x00000010
-#endif
-
-#ifndef ISC_RET_ALLOCATED_MEMORY
-#define ISC_RET_ALLOCATED_MEMORY 0x00000100
-#endif
-
-#ifndef ISC_RET_STREAM
-#define ISC_RET_STREAM 0x00008000
-#endif
-
-#ifndef SEC_E_INSUFFICIENT_MEMORY
-# define SEC_E_INSUFFICIENT_MEMORY ((HRESULT)0x80090300L)
-#endif
-#ifndef SEC_E_INVALID_HANDLE
-# define SEC_E_INVALID_HANDLE ((HRESULT)0x80090301L)
-#endif
-#ifndef SEC_E_UNSUPPORTED_FUNCTION
-# define SEC_E_UNSUPPORTED_FUNCTION ((HRESULT)0x80090302L)
-#endif
-#ifndef SEC_E_TARGET_UNKNOWN
-# define SEC_E_TARGET_UNKNOWN ((HRESULT)0x80090303L)
-#endif
-#ifndef SEC_E_INTERNAL_ERROR
-# define SEC_E_INTERNAL_ERROR ((HRESULT)0x80090304L)
-#endif
-#ifndef SEC_E_SECPKG_NOT_FOUND
-# define SEC_E_SECPKG_NOT_FOUND ((HRESULT)0x80090305L)
-#endif
-#ifndef SEC_E_NOT_OWNER
-# define SEC_E_NOT_OWNER ((HRESULT)0x80090306L)
-#endif
-#ifndef SEC_E_CANNOT_INSTALL
-# define SEC_E_CANNOT_INSTALL ((HRESULT)0x80090307L)
-#endif
-#ifndef SEC_E_INVALID_TOKEN
-# define SEC_E_INVALID_TOKEN ((HRESULT)0x80090308L)
-#endif
-#ifndef SEC_E_CANNOT_PACK
-# define SEC_E_CANNOT_PACK ((HRESULT)0x80090309L)
-#endif
-#ifndef SEC_E_QOP_NOT_SUPPORTED
-# define SEC_E_QOP_NOT_SUPPORTED ((HRESULT)0x8009030AL)
-#endif
-#ifndef SEC_E_NO_IMPERSONATION
-# define SEC_E_NO_IMPERSONATION ((HRESULT)0x8009030BL)
-#endif
-#ifndef SEC_E_LOGON_DENIED
-# define SEC_E_LOGON_DENIED ((HRESULT)0x8009030CL)
-#endif
-#ifndef SEC_E_UNKNOWN_CREDENTIALS
-# define SEC_E_UNKNOWN_CREDENTIALS ((HRESULT)0x8009030DL)
-#endif
-#ifndef SEC_E_NO_CREDENTIALS
-# define SEC_E_NO_CREDENTIALS ((HRESULT)0x8009030EL)
-#endif
-#ifndef SEC_E_MESSAGE_ALTERED
-# define SEC_E_MESSAGE_ALTERED ((HRESULT)0x8009030FL)
-#endif
-#ifndef SEC_E_OUT_OF_SEQUENCE
-# define SEC_E_OUT_OF_SEQUENCE ((HRESULT)0x80090310L)
-#endif
-#ifndef SEC_E_NO_AUTHENTICATING_AUTHORITY
-# define SEC_E_NO_AUTHENTICATING_AUTHORITY ((HRESULT)0x80090311L)
-#endif
-#ifndef SEC_E_BAD_PKGID
-# define SEC_E_BAD_PKGID ((HRESULT)0x80090316L)
-#endif
-#ifndef SEC_E_CONTEXT_EXPIRED
-# define SEC_E_CONTEXT_EXPIRED ((HRESULT)0x80090317L)
-#endif
-#ifndef SEC_E_INCOMPLETE_MESSAGE
-# define SEC_E_INCOMPLETE_MESSAGE ((HRESULT)0x80090318L)
-#endif
-#ifndef SEC_E_INCOMPLETE_CREDENTIALS
-# define SEC_E_INCOMPLETE_CREDENTIALS ((HRESULT)0x80090320L)
-#endif
-#ifndef SEC_E_BUFFER_TOO_SMALL
-# define SEC_E_BUFFER_TOO_SMALL ((HRESULT)0x80090321L)
-#endif
-#ifndef SEC_E_WRONG_PRINCIPAL
-# define SEC_E_WRONG_PRINCIPAL ((HRESULT)0x80090322L)
-#endif
-#ifndef SEC_E_TIME_SKEW
-# define SEC_E_TIME_SKEW ((HRESULT)0x80090324L)
-#endif
-#ifndef SEC_E_UNTRUSTED_ROOT
-# define SEC_E_UNTRUSTED_ROOT ((HRESULT)0x80090325L)
-#endif
-#ifndef SEC_E_ILLEGAL_MESSAGE
-# define SEC_E_ILLEGAL_MESSAGE ((HRESULT)0x80090326L)
-#endif
-#ifndef SEC_E_CERT_UNKNOWN
-# define SEC_E_CERT_UNKNOWN ((HRESULT)0x80090327L)
-#endif
-#ifndef SEC_E_CERT_EXPIRED
-# define SEC_E_CERT_EXPIRED ((HRESULT)0x80090328L)
-#endif
-#ifndef SEC_E_ENCRYPT_FAILURE
-# define SEC_E_ENCRYPT_FAILURE ((HRESULT)0x80090329L)
-#endif
-#ifndef SEC_E_DECRYPT_FAILURE
-# define SEC_E_DECRYPT_FAILURE ((HRESULT)0x80090330L)
-#endif
-#ifndef SEC_E_ALGORITHM_MISMATCH
-# define SEC_E_ALGORITHM_MISMATCH ((HRESULT)0x80090331L)
-#endif
-#ifndef SEC_E_SECURITY_QOS_FAILED
-# define SEC_E_SECURITY_QOS_FAILED ((HRESULT)0x80090332L)
-#endif
-#ifndef SEC_E_UNFINISHED_CONTEXT_DELETED
-# define SEC_E_UNFINISHED_CONTEXT_DELETED ((HRESULT)0x80090333L)
-#endif
-#ifndef SEC_E_NO_TGT_REPLY
-# define SEC_E_NO_TGT_REPLY ((HRESULT)0x80090334L)
-#endif
-#ifndef SEC_E_NO_IP_ADDRESSES
-# define SEC_E_NO_IP_ADDRESSES ((HRESULT)0x80090335L)
-#endif
-#ifndef SEC_E_WRONG_CREDENTIAL_HANDLE
-# define SEC_E_WRONG_CREDENTIAL_HANDLE ((HRESULT)0x80090336L)
-#endif
-#ifndef SEC_E_CRYPTO_SYSTEM_INVALID
-# define SEC_E_CRYPTO_SYSTEM_INVALID ((HRESULT)0x80090337L)
-#endif
-#ifndef SEC_E_MAX_REFERRALS_EXCEEDED
-# define SEC_E_MAX_REFERRALS_EXCEEDED ((HRESULT)0x80090338L)
-#endif
-#ifndef SEC_E_MUST_BE_KDC
-# define SEC_E_MUST_BE_KDC ((HRESULT)0x80090339L)
-#endif
-#ifndef SEC_E_STRONG_CRYPTO_NOT_SUPPORTED
-# define SEC_E_STRONG_CRYPTO_NOT_SUPPORTED ((HRESULT)0x8009033AL)
-#endif
-#ifndef SEC_E_TOO_MANY_PRINCIPALS
-# define SEC_E_TOO_MANY_PRINCIPALS ((HRESULT)0x8009033BL)
-#endif
-#ifndef SEC_E_NO_PA_DATA
-# define SEC_E_NO_PA_DATA ((HRESULT)0x8009033CL)
-#endif
-#ifndef SEC_E_PKINIT_NAME_MISMATCH
-# define SEC_E_PKINIT_NAME_MISMATCH ((HRESULT)0x8009033DL)
-#endif
-#ifndef SEC_E_SMARTCARD_LOGON_REQUIRED
-# define SEC_E_SMARTCARD_LOGON_REQUIRED ((HRESULT)0x8009033EL)
-#endif
-#ifndef SEC_E_SHUTDOWN_IN_PROGRESS
-# define SEC_E_SHUTDOWN_IN_PROGRESS ((HRESULT)0x8009033FL)
-#endif
-#ifndef SEC_E_KDC_INVALID_REQUEST
-# define SEC_E_KDC_INVALID_REQUEST ((HRESULT)0x80090340L)
-#endif
-#ifndef SEC_E_KDC_UNABLE_TO_REFER
-# define SEC_E_KDC_UNABLE_TO_REFER ((HRESULT)0x80090341L)
-#endif
-#ifndef SEC_E_KDC_UNKNOWN_ETYPE
-# define SEC_E_KDC_UNKNOWN_ETYPE ((HRESULT)0x80090342L)
-#endif
-#ifndef SEC_E_UNSUPPORTED_PREAUTH
-# define SEC_E_UNSUPPORTED_PREAUTH ((HRESULT)0x80090343L)
-#endif
-#ifndef SEC_E_DELEGATION_REQUIRED
-# define SEC_E_DELEGATION_REQUIRED ((HRESULT)0x80090345L)
-#endif
-#ifndef SEC_E_BAD_BINDINGS
-# define SEC_E_BAD_BINDINGS ((HRESULT)0x80090346L)
-#endif
-#ifndef SEC_E_MULTIPLE_ACCOUNTS
-# define SEC_E_MULTIPLE_ACCOUNTS ((HRESULT)0x80090347L)
-#endif
-#ifndef SEC_E_NO_KERB_KEY
-# define SEC_E_NO_KERB_KEY ((HRESULT)0x80090348L)
-#endif
-#ifndef SEC_E_CERT_WRONG_USAGE
-# define SEC_E_CERT_WRONG_USAGE ((HRESULT)0x80090349L)
-#endif
-#ifndef SEC_E_DOWNGRADE_DETECTED
-# define SEC_E_DOWNGRADE_DETECTED ((HRESULT)0x80090350L)
-#endif
-#ifndef SEC_E_SMARTCARD_CERT_REVOKED
-# define SEC_E_SMARTCARD_CERT_REVOKED ((HRESULT)0x80090351L)
-#endif
-#ifndef SEC_E_ISSUING_CA_UNTRUSTED
-# define SEC_E_ISSUING_CA_UNTRUSTED ((HRESULT)0x80090352L)
-#endif
-#ifndef SEC_E_REVOCATION_OFFLINE_C
-# define SEC_E_REVOCATION_OFFLINE_C ((HRESULT)0x80090353L)
-#endif
-#ifndef SEC_E_PKINIT_CLIENT_FAILURE
-# define SEC_E_PKINIT_CLIENT_FAILURE ((HRESULT)0x80090354L)
-#endif
-#ifndef SEC_E_SMARTCARD_CERT_EXPIRED
-# define SEC_E_SMARTCARD_CERT_EXPIRED ((HRESULT)0x80090355L)
-#endif
-#ifndef SEC_E_NO_S4U_PROT_SUPPORT
-# define SEC_E_NO_S4U_PROT_SUPPORT ((HRESULT)0x80090356L)
-#endif
-#ifndef SEC_E_CROSSREALM_DELEGATION_FAILURE
-# define SEC_E_CROSSREALM_DELEGATION_FAILURE ((HRESULT)0x80090357L)
-#endif
-#ifndef SEC_E_REVOCATION_OFFLINE_KDC
-# define SEC_E_REVOCATION_OFFLINE_KDC ((HRESULT)0x80090358L)
-#endif
-#ifndef SEC_E_ISSUING_CA_UNTRUSTED_KDC
-# define SEC_E_ISSUING_CA_UNTRUSTED_KDC ((HRESULT)0x80090359L)
-#endif
-#ifndef SEC_E_KDC_CERT_EXPIRED
-# define SEC_E_KDC_CERT_EXPIRED ((HRESULT)0x8009035AL)
-#endif
-#ifndef SEC_E_KDC_CERT_REVOKED
-# define SEC_E_KDC_CERT_REVOKED ((HRESULT)0x8009035BL)
-#endif
#ifndef SEC_E_INVALID_PARAMETER
# define SEC_E_INVALID_PARAMETER ((HRESULT)0x8009035DL)
#endif
@@ -301,30 +80,6 @@ extern PSecurityFunctionTable s_pSecFn;
# define SEC_E_POLICY_NLTM_ONLY ((HRESULT)0x8009035FL)
#endif
-#ifndef SEC_I_CONTINUE_NEEDED
-# define SEC_I_CONTINUE_NEEDED ((HRESULT)0x00090312L)
-#endif
-#ifndef SEC_I_COMPLETE_NEEDED
-# define SEC_I_COMPLETE_NEEDED ((HRESULT)0x00090313L)
-#endif
-#ifndef SEC_I_COMPLETE_AND_CONTINUE
-# define SEC_I_COMPLETE_AND_CONTINUE ((HRESULT)0x00090314L)
-#endif
-#ifndef SEC_I_LOCAL_LOGON
-# define SEC_I_LOCAL_LOGON ((HRESULT)0x00090315L)
-#endif
-#ifndef SEC_I_CONTEXT_EXPIRED
-# define SEC_I_CONTEXT_EXPIRED ((HRESULT)0x00090317L)
-#endif
-#ifndef SEC_I_INCOMPLETE_CREDENTIALS
-# define SEC_I_INCOMPLETE_CREDENTIALS ((HRESULT)0x00090320L)
-#endif
-#ifndef SEC_I_RENEGOTIATE
-# define SEC_I_RENEGOTIATE ((HRESULT)0x00090321L)
-#endif
-#ifndef SEC_I_NO_LSA_CONTEXT
-# define SEC_I_NO_LSA_CONTEXT ((HRESULT)0x00090323L)
-#endif
#ifndef SEC_I_SIGNATURE_NEEDED
# define SEC_I_SIGNATURE_NEEDED ((HRESULT)0x0009035CL)
#endif
diff --git a/Utilities/cmcurl/lib/curl_threads.c b/Utilities/cmcurl/lib/curl_threads.c
index e13e294..222d936 100644
--- a/Utilities/cmcurl/lib/curl_threads.c
+++ b/Utilities/cmcurl/lib/curl_threads.c
@@ -106,8 +106,6 @@ curl_thread_t Curl_thread_create(unsigned int (CURL_STDCALL *func) (void *),
{
#ifdef _WIN32_WCE
typedef HANDLE curl_win_thread_handle_t;
-#elif defined(__MINGW32__) && !defined(__MINGW64_VERSION_MAJOR)
- typedef unsigned long curl_win_thread_handle_t;
#else
typedef uintptr_t curl_win_thread_handle_t;
#endif
diff --git a/Utilities/cmcurl/lib/curl_threads.h b/Utilities/cmcurl/lib/curl_threads.h
index facbc73..27a478d 100644
--- a/Utilities/cmcurl/lib/curl_threads.h
+++ b/Utilities/cmcurl/lib/curl_threads.h
@@ -40,8 +40,7 @@
# define curl_thread_t HANDLE
# define curl_thread_t_null (HANDLE)0
# if !defined(_WIN32_WINNT) || !defined(_WIN32_WINNT_VISTA) || \
- (_WIN32_WINNT < _WIN32_WINNT_VISTA) || \
- (defined(__MINGW32__) && !defined(__MINGW64_VERSION_MAJOR))
+ (_WIN32_WINNT < _WIN32_WINNT_VISTA)
# define Curl_mutex_init(m) InitializeCriticalSection(m)
# else
# define Curl_mutex_init(m) InitializeCriticalSectionEx(m, 0, 1)
diff --git a/Utilities/cmcurl/lib/curl_trc.c b/Utilities/cmcurl/lib/curl_trc.c
index 76c35ba..e53b305 100644
--- a/Utilities/cmcurl/lib/curl_trc.c
+++ b/Utilities/cmcurl/lib/curl_trc.c
@@ -61,6 +61,10 @@ void Curl_debug(struct Curl_easy *data, curl_infotype type,
"* ", "< ", "> ", "{ ", "} ", "{ ", "} " };
if(data->set.fdebug) {
bool inCallback = Curl_is_in_callback(data);
+ /* CURLOPT_DEBUGFUNCTION doc says the user may set CURLOPT_PRIVATE to
+ distinguish their handle from internal handles. */
+ if(data->internal)
+ DEBUGASSERT(!data->set.private_data);
Curl_set_in_callback(data, true);
(void)(*data->set.fdebug)(data, type, ptr, size, data->set.debugdata);
Curl_set_in_callback(data, inCallback);
diff --git a/Utilities/cmcurl/lib/doh.c b/Utilities/cmcurl/lib/doh.c
index 7a38eab..bb0c89e 100644
--- a/Utilities/cmcurl/lib/doh.c
+++ b/Utilities/cmcurl/lib/doh.c
@@ -242,6 +242,7 @@ static CURLcode dohprobe(struct Curl_easy *data,
/* pass in the struct pointer via a local variable to please coverity and
the gcc typecheck helpers */
struct dynbuf *resp = &p->serverdoh;
+ doh->internal = true;
ERROR_CHECK_SETOPT(CURLOPT_URL, url);
ERROR_CHECK_SETOPT(CURLOPT_DEFAULT_PROTOCOL, "https");
ERROR_CHECK_SETOPT(CURLOPT_WRITEFUNCTION, doh_write_cb);
@@ -307,6 +308,10 @@ static CURLcode dohprobe(struct Curl_easy *data,
ERROR_CHECK_SETOPT(CURLOPT_SSL_CTX_FUNCTION, data->set.ssl.fsslctx);
if(data->set.ssl.fsslctxp)
ERROR_CHECK_SETOPT(CURLOPT_SSL_CTX_DATA, data->set.ssl.fsslctxp);
+ if(data->set.fdebug)
+ ERROR_CHECK_SETOPT(CURLOPT_DEBUGFUNCTION, data->set.fdebug);
+ if(data->set.debugdata)
+ ERROR_CHECK_SETOPT(CURLOPT_DEBUGDATA, data->set.debugdata);
if(data->set.str[STRING_SSL_EC_CURVES]) {
ERROR_CHECK_SETOPT(CURLOPT_SSL_EC_CURVES,
data->set.str[STRING_SSL_EC_CURVES]);
diff --git a/Utilities/cmcurl/lib/dynbuf.h b/Utilities/cmcurl/lib/dynbuf.h
index 6291eab..31a9130 100644
--- a/Utilities/cmcurl/lib/dynbuf.h
+++ b/Utilities/cmcurl/lib/dynbuf.h
@@ -89,4 +89,5 @@ int Curl_dyn_vprintf(struct dynbuf *dyn, const char *format, va_list ap_save);
#define DYN_H1_TRAILER 4096
#define DYN_PINGPPONG_CMD (64*1024)
#define DYN_IMAP_CMD (64*1024)
+#define DYN_MQTT_RECV (64*1024)
#endif
diff --git a/Utilities/cmcurl/lib/dynhds.c b/Utilities/cmcurl/lib/dynhds.c
index 007dfc5..979b3e8 100644
--- a/Utilities/cmcurl/lib/dynhds.c
+++ b/Utilities/cmcurl/lib/dynhds.c
@@ -344,6 +344,8 @@ size_t Curl_dynhds_cremove(struct dynhds *dynhds, const char *name)
return Curl_dynhds_remove(dynhds, name, strlen(name));
}
+#endif
+
CURLcode Curl_dynhds_h1_dprint(struct dynhds *dynhds, struct dynbuf *dbuf)
{
CURLcode result = CURLE_OK;
@@ -363,4 +365,3 @@ CURLcode Curl_dynhds_h1_dprint(struct dynhds *dynhds, struct dynbuf *dbuf)
return result;
}
-#endif
diff --git a/Utilities/cmcurl/lib/easy.c b/Utilities/cmcurl/lib/easy.c
index 16bbd35..6b4fb8e 100644
--- a/Utilities/cmcurl/lib/easy.c
+++ b/Utilities/cmcurl/lib/easy.c
@@ -303,9 +303,6 @@ void curl_global_cleanup(void)
Curl_ssh_cleanup();
-#ifdef USE_WOLFSSH
- (void)wolfSSH_Cleanup();
-#endif
#ifdef DEBUGBUILD
free(leakpointer);
#endif
@@ -925,9 +922,7 @@ struct Curl_easy *curl_easy_duphandle(struct Curl_easy *data)
if(data->cookies) {
/* If cookies are enabled in the parent handle, we enable them
in the clone as well! */
- outcurl->cookies = Curl_cookie_init(data,
- data->cookies->filename,
- outcurl->cookies,
+ outcurl->cookies = Curl_cookie_init(data, NULL, outcurl->cookies,
data->set.cookiesession);
if(!outcurl->cookies)
goto fail;
@@ -1088,11 +1083,14 @@ CURLcode curl_easy_pause(struct Curl_easy *data, int action)
CURLcode result = CURLE_OK;
int oldstate;
int newstate;
+ bool recursive = FALSE;
if(!GOOD_EASY_HANDLE(data) || !data->conn)
/* crazy input, don't continue */
return CURLE_BAD_FUNCTION_ARGUMENT;
+ if(Curl_is_in_callback(data))
+ recursive = TRUE;
k = &data->req;
oldstate = k->keepon & (KEEP_RECV_PAUSE| KEEP_SEND_PAUSE);
@@ -1120,34 +1118,9 @@ CURLcode curl_easy_pause(struct Curl_easy *data, int action)
if(!(newstate & KEEP_RECV_PAUSE)) {
Curl_conn_ev_data_pause(data, FALSE);
-
- if(data->state.tempcount) {
- /* there are buffers for sending that can be delivered as the receive
- pausing is lifted! */
- unsigned int i;
- unsigned int count = data->state.tempcount;
- struct tempbuf writebuf[3]; /* there can only be three */
-
- /* copy the structs to allow for immediate re-pausing */
- for(i = 0; i < data->state.tempcount; i++) {
- writebuf[i] = data->state.tempwrite[i];
- Curl_dyn_init(&data->state.tempwrite[i].b, DYN_PAUSE_BUFFER);
- }
- data->state.tempcount = 0;
-
- for(i = 0; i < count; i++) {
- /* even if one function returns error, this loops through and frees
- all buffers */
- if(!result)
- result = Curl_client_write(data, writebuf[i].type,
- Curl_dyn_ptr(&writebuf[i].b),
- Curl_dyn_len(&writebuf[i].b));
- Curl_dyn_free(&writebuf[i].b);
- }
-
- if(result)
- return result;
- }
+ result = Curl_client_unpause(data);
+ if(result)
+ return result;
}
#ifdef USE_HYPER
@@ -1184,6 +1157,11 @@ CURLcode curl_easy_pause(struct Curl_easy *data, int action)
corresponding socket callback, if used */
result = Curl_updatesocket(data);
+ if(recursive)
+ /* this might have called a callback recursively which might have set this
+ to false again on exit */
+ Curl_set_in_callback(data, TRUE);
+
return result;
}
diff --git a/Utilities/cmcurl/lib/easy_lock.h b/Utilities/cmcurl/lib/easy_lock.h
index 6399a39..d3fffd0 100644
--- a/Utilities/cmcurl/lib/easy_lock.h
+++ b/Utilities/cmcurl/lib/easy_lock.h
@@ -31,13 +31,6 @@
#if defined(_WIN32_WINNT) && _WIN32_WINNT >= 0x600
#ifdef __MINGW32__
-#ifndef __MINGW64_VERSION_MAJOR
-#if (__MINGW32_MAJOR_VERSION < 5) || \
- (__MINGW32_MAJOR_VERSION == 5 && __MINGW32_MINOR_VERSION == 0)
-/* mingw >= 5.0.1 defines SRWLOCK, and slightly different from MS define */
-typedef PVOID SRWLOCK, *PSRWLOCK;
-#endif
-#endif
#ifndef SRWLOCK_INIT
#define SRWLOCK_INIT NULL
#endif
diff --git a/Utilities/cmcurl/lib/escape.c b/Utilities/cmcurl/lib/escape.c
index 56aa2b3..5af00c3 100644
--- a/Utilities/cmcurl/lib/escape.c
+++ b/Utilities/cmcurl/lib/escape.c
@@ -38,33 +38,6 @@
#include "curl_memory.h"
#include "memdebug.h"
-/* Portable character check (remember EBCDIC). Do not use isalnum() because
- its behavior is altered by the current locale.
- See https://datatracker.ietf.org/doc/html/rfc3986#section-2.3
-*/
-bool Curl_isunreserved(unsigned char in)
-{
- switch(in) {
- case '0': case '1': case '2': case '3': case '4':
- case '5': case '6': case '7': case '8': case '9':
- case 'a': case 'b': case 'c': case 'd': case 'e':
- case 'f': case 'g': case 'h': case 'i': case 'j':
- case 'k': case 'l': case 'm': case 'n': case 'o':
- case 'p': case 'q': case 'r': case 's': case 't':
- case 'u': case 'v': case 'w': case 'x': case 'y': case 'z':
- case 'A': case 'B': case 'C': case 'D': case 'E':
- case 'F': case 'G': case 'H': case 'I': case 'J':
- case 'K': case 'L': case 'M': case 'N': case 'O':
- case 'P': case 'Q': case 'R': case 'S': case 'T':
- case 'U': case 'V': case 'W': case 'X': case 'Y': case 'Z':
- case '-': case '.': case '_': case '~':
- return TRUE;
- default:
- break;
- }
- return FALSE;
-}
-
/* for ABI-compatibility with previous versions */
char *curl_escape(const char *string, int inlength)
{
@@ -99,7 +72,7 @@ char *curl_easy_escape(struct Curl_easy *data, const char *string,
while(length--) {
unsigned char in = *string++; /* treat the characters unsigned */
- if(Curl_isunreserved(in)) {
+ if(ISUNRESERVED(in)) {
/* append this */
if(Curl_dyn_addn(&d, &in, 1))
return NULL;
@@ -233,3 +206,29 @@ void curl_free(void *p)
{
free(p);
}
+
+/*
+ * Curl_hexencode()
+ *
+ * Converts binary input to lowercase hex-encoded ASCII output.
+ * Null-terminated.
+ */
+void Curl_hexencode(const unsigned char *src, size_t len, /* input length */
+ unsigned char *out, size_t olen) /* output buffer size */
+{
+ const char *hex = "0123456789abcdef";
+ DEBUGASSERT(src && len && (olen >= 3));
+ if(src && len && (olen >= 3)) {
+ while(len-- && (olen >= 3)) {
+ /* clang-tidy warns on this line without this comment: */
+ /* NOLINTNEXTLINE(clang-analyzer-core.UndefinedBinaryOperatorResult) */
+ *out++ = hex[(*src & 0xF0)>>4];
+ *out++ = hex[*src & 0x0F];
+ ++src;
+ olen -= 2;
+ }
+ *out = 0;
+ }
+ else if(olen)
+ *out = 0;
+}
diff --git a/Utilities/cmcurl/lib/escape.h b/Utilities/cmcurl/lib/escape.h
index cdbb712..690e417 100644
--- a/Utilities/cmcurl/lib/escape.h
+++ b/Utilities/cmcurl/lib/escape.h
@@ -26,7 +26,7 @@
/* Escape and unescape URL encoding in strings. The functions return a new
* allocated string or NULL if an error occurred. */
-bool Curl_isunreserved(unsigned char in);
+#include "curl_ctype.h"
enum urlreject {
REJECT_NADA = 2,
@@ -38,4 +38,7 @@ CURLcode Curl_urldecode(const char *string, size_t length,
char **ostring, size_t *olen,
enum urlreject ctrl);
+void Curl_hexencode(const unsigned char *src, size_t len, /* input length */
+ unsigned char *out, size_t olen); /* output buffer size */
+
#endif /* HEADER_CURL_ESCAPE_H */
diff --git a/Utilities/cmcurl/lib/file.c b/Utilities/cmcurl/lib/file.c
index c751e88..ffa9fb7 100644
--- a/Utilities/cmcurl/lib/file.c
+++ b/Utilities/cmcurl/lib/file.c
@@ -571,7 +571,9 @@ static CURLcode file_do(struct Curl_easy *data, bool *done)
if(result)
return result;
- Curl_pgrsSetDownloadCounter(data, bytecount);
+ result = Curl_pgrsSetDownloadCounter(data, bytecount);
+ if(result)
+ return result;
if(Curl_pgrsUpdate(data))
result = CURLE_ABORTED_BY_CALLBACK;
diff --git a/Utilities/cmcurl/lib/fopen.c b/Utilities/cmcurl/lib/fopen.c
index b6e3cad..75b8a7a 100644
--- a/Utilities/cmcurl/lib/fopen.c
+++ b/Utilities/cmcurl/lib/fopen.c
@@ -64,7 +64,7 @@ CURLcode Curl_fopen(struct Curl_easy *data, const char *filename,
fclose(*fh);
*fh = NULL;
- result = Curl_rand_hex(data, randsuffix, sizeof(randsuffix));
+ result = Curl_rand_alnum(data, randsuffix, sizeof(randsuffix));
if(result)
goto fail;
diff --git a/Utilities/cmcurl/lib/formdata.c b/Utilities/cmcurl/lib/formdata.c
index 8984b63..e40c4bc 100644
--- a/Utilities/cmcurl/lib/formdata.c
+++ b/Utilities/cmcurl/lib/formdata.c
@@ -789,6 +789,20 @@ static CURLcode setname(curl_mimepart *part, const char *name, size_t len)
return res;
}
+/* wrap call to fseeko so it matches the calling convention of callback */
+static int fseeko_wrapper(void *stream, curl_off_t offset, int whence)
+{
+#if defined(HAVE_FSEEKO)
+ return fseeko(stream, (off_t)offset, whence);
+#elif defined(HAVE__FSEEKI64)
+ return _fseeki64(stream, (__int64)offset, whence);
+#else
+ if(offset > LONG_MAX)
+ return -1;
+ return fseek(stream, (long)offset, whence);
+#endif
+}
+
/*
* Curl_getformdata() converts a linked list of "meta data" into a mime
* structure. The input list is in 'post', while the output is stored in
@@ -874,8 +888,7 @@ CURLcode Curl_getformdata(struct Curl_easy *data,
compatibility: use of "-" pseudo file name should be avoided. */
result = curl_mime_data_cb(part, (curl_off_t) -1,
(curl_read_callback) fread,
- CURLX_FUNCTION_CAST(curl_seek_callback,
- fseek),
+ fseeko_wrapper,
NULL, (void *) stdin);
}
else
diff --git a/Utilities/cmcurl/lib/ftp.c b/Utilities/cmcurl/lib/ftp.c
index 0ba8742..6e7fda0 100644
--- a/Utilities/cmcurl/lib/ftp.c
+++ b/Utilities/cmcurl/lib/ftp.c
@@ -2067,6 +2067,31 @@ static bool ftp_213_date(const char *p, int *year, int *month, int *day,
return TRUE;
}
+static CURLcode client_write_header(struct Curl_easy *data,
+ char *buf, size_t blen)
+{
+ /* Some replies from an FTP server are written to the client
+ * as CLIENTWRITE_HEADER, formatted as if they came from a
+ * HTTP conversation.
+ * In all protocols, CLIENTWRITE_HEADER data is only passed to
+ * the body write callback when data->set.include_header is set
+ * via CURLOPT_HEADER.
+ * For historic reasons, FTP never played this game and expects
+ * all its HEADERs to do that always. Set that flag during the
+ * call to Curl_client_write() so it does the right thing.
+ *
+ * Notice that we cannot enable this flag for FTP in general,
+ * as an FTP transfer might involve a HTTP proxy connection and
+ * headers from CONNECT should not automatically be part of the
+ * output. */
+ CURLcode result;
+ int save = data->set.include_header;
+ data->set.include_header = TRUE;
+ result = Curl_client_write(data, CLIENTWRITE_HEADER, buf, blen);
+ data->set.include_header = save? TRUE:FALSE;
+ return result;
+}
+
static CURLcode ftp_state_mdtm_resp(struct Curl_easy *data,
int ftpcode)
{
@@ -2120,8 +2145,7 @@ static CURLcode ftp_state_mdtm_resp(struct Curl_easy *data,
tm->tm_hour,
tm->tm_min,
tm->tm_sec);
- result = Curl_client_write(data, CLIENTWRITE_BOTH, headerbuf,
- headerbuflen);
+ result = client_write_header(data, headerbuf, headerbuflen);
if(result)
return result;
} /* end of a ridiculous amount of conditionals */
@@ -2331,7 +2355,7 @@ static CURLcode ftp_state_size_resp(struct Curl_easy *data,
char clbuf[128];
int clbuflen = msnprintf(clbuf, sizeof(clbuf),
"Content-Length: %" CURL_FORMAT_CURL_OFF_T "\r\n", filesize);
- result = Curl_client_write(data, CLIENTWRITE_BOTH, clbuf, clbuflen);
+ result = client_write_header(data, clbuf, clbuflen);
if(result)
return result;
}
@@ -2365,8 +2389,7 @@ static CURLcode ftp_state_rest_resp(struct Curl_easy *data,
#ifdef CURL_FTP_HTTPSTYLE_HEAD
if(ftpcode == 350) {
char buffer[24]= { "Accept-ranges: bytes\r\n" };
- result = Curl_client_write(data, CLIENTWRITE_BOTH, buffer,
- strlen(buffer));
+ result = client_write_header(data, buffer, strlen(buffer));
if(result)
return result;
}
@@ -3457,7 +3480,7 @@ CURLcode ftp_sendquote(struct Curl_easy *data,
/* if a command starts with an asterisk, which a legal FTP command never
can, the command will be allowed to fail without it causing any
aborts or cancels etc. It will cause libcurl to act as if the command
- is successful, whatever the server reponds. */
+ is successful, whatever the server responds. */
if(cmd[0] == '*') {
cmd++;
diff --git a/Utilities/cmcurl/lib/ftplistparser.c b/Utilities/cmcurl/lib/ftplistparser.c
index 226d9bc..2a7ca5b 100644
--- a/Utilities/cmcurl/lib/ftplistparser.c
+++ b/Utilities/cmcurl/lib/ftplistparser.c
@@ -379,7 +379,7 @@ size_t Curl_ftp_parselist(char *buffer, size_t size, size_t nmemb,
/* scenario:
* 1. call => OK..
* 2. call => OUT_OF_MEMORY (or other error)
- * 3. (last) call => is skipped RIGHT HERE and the error is hadled later
+ * 3. (last) call => is skipped RIGHT HERE and the error is handled later
* in wc_statemach()
*/
goto fail;
diff --git a/Utilities/cmcurl/lib/hmac.c b/Utilities/cmcurl/lib/hmac.c
index 87e7be8..4019b67 100644
--- a/Utilities/cmcurl/lib/hmac.c
+++ b/Utilities/cmcurl/lib/hmac.c
@@ -26,8 +26,8 @@
#include "curl_setup.h"
-#if (defined(USE_CURL_NTLM_CORE) && !defined(USE_WINDOWS_SSPI)) \
- || !defined(CURL_DISABLE_AWS)
+#if (defined(USE_CURL_NTLM_CORE) && !defined(USE_WINDOWS_SSPI)) \
+ || !defined(CURL_DISABLE_AWS) || !defined(CURL_DISABLE_DIGEST_AUTH)
#include <curl/curl.h>
diff --git a/Utilities/cmcurl/lib/hostip.c b/Utilities/cmcurl/lib/hostip.c
index acb4b51..3cd9a65 100644
--- a/Utilities/cmcurl/lib/hostip.c
+++ b/Utilities/cmcurl/lib/hostip.c
@@ -41,12 +41,8 @@
#include <inet.h>
#endif
-#ifdef HAVE_SETJMP_H
#include <setjmp.h>
-#endif
-#ifdef HAVE_SIGNAL_H
#include <signal.h>
-#endif
#include "urldata.h"
#include "sendf.h"
diff --git a/Utilities/cmcurl/lib/hostip.h b/Utilities/cmcurl/lib/hostip.h
index 06d0867..b68f539 100644
--- a/Utilities/cmcurl/lib/hostip.h
+++ b/Utilities/cmcurl/lib/hostip.h
@@ -30,9 +30,7 @@
#include "timeval.h" /* for timediff_t */
#include "asyn.h"
-#ifdef HAVE_SETJMP_H
#include <setjmp.h>
-#endif
/* Allocate enough memory to hold the full name information structs and
* everything. OSF1 is known to require at least 8872 bytes. The buffer
diff --git a/Utilities/cmcurl/lib/http.c b/Utilities/cmcurl/lib/http.c
index 4344b9d..40ef70d 100644
--- a/Utilities/cmcurl/lib/http.c
+++ b/Utilities/cmcurl/lib/http.c
@@ -1139,6 +1139,8 @@ CURLcode Curl_http_input_auth(struct Curl_easy *data, bool proxy,
data->state.authproblem = TRUE;
}
}
+#else
+ ;
#endif
/* there may be multiple methods on one line, so keep reading */
@@ -1157,8 +1159,6 @@ CURLcode Curl_http_input_auth(struct Curl_easy *data, bool proxy,
* http_should_fail() determines whether an HTTP response has gotten us
* into an error state or not.
*
- * @param conn all information about the current connection
- *
* @retval FALSE communications should continue
*
* @retval TRUE communications should not continue
@@ -1602,8 +1602,6 @@ CURLcode Curl_http_done(struct Curl_easy *data,
data->state.authhost.multipass = FALSE;
data->state.authproxy.multipass = FALSE;
- Curl_unencode_cleanup(data);
-
/* set the proper values (possibly modified on POST) */
conn->seek_func = data->set.seek_func; /* restore */
conn->seek_client = data->set.seek_client; /* restore */
@@ -3970,18 +3968,23 @@ CURLcode Curl_bump_headersize(struct Curl_easy *data,
bool connect_only)
{
size_t bad = 0;
+ unsigned int max = MAX_HTTP_RESP_HEADER_SIZE;
if(delta < MAX_HTTP_RESP_HEADER_SIZE) {
+ data->info.header_size += (unsigned int)delta;
+ data->req.allheadercount += (unsigned int)delta;
if(!connect_only)
data->req.headerbytecount += (unsigned int)delta;
- data->info.header_size += (unsigned int)delta;
- if(data->info.header_size > MAX_HTTP_RESP_HEADER_SIZE)
+ if(data->req.allheadercount > max)
+ bad = data->req.allheadercount;
+ else if(data->info.header_size > (max * 20)) {
bad = data->info.header_size;
+ max *= 20;
+ }
}
else
- bad = data->info.header_size + delta;
+ bad = data->req.allheadercount + delta;
if(bad) {
- failf(data, "Too large response headers: %zu > %u",
- bad, MAX_HTTP_RESP_HEADER_SIZE);
+ failf(data, "Too large response headers: %zu > %u", bad, max);
return CURLE_RECV_ERROR;
}
return CURLE_OK;
@@ -4231,7 +4234,6 @@ CURLcode Curl_http_readwrite_headers(struct Curl_easy *data,
/* now, only output this if the header AND body are requested:
*/
writetype = CLIENTWRITE_HEADER |
- (data->set.include_header ? CLIENTWRITE_BODY : 0) |
((k->httpcode/100 == 1) ? CLIENTWRITE_1XX : 0);
headerlen = Curl_dyn_len(&data->state.headerb);
@@ -4563,8 +4565,6 @@ CURLcode Curl_http_readwrite_headers(struct Curl_easy *data,
/*
* End of header-checks. Write them to the client.
*/
- if(data->set.include_header)
- writetype |= CLIENTWRITE_BODY;
if(k->httpcode/100 == 1)
writetype |= CLIENTWRITE_1XX;
diff --git a/Utilities/cmcurl/lib/http1.c b/Utilities/cmcurl/lib/http1.c
index 1ca7d41..182234c 100644
--- a/Utilities/cmcurl/lib/http1.c
+++ b/Utilities/cmcurl/lib/http1.c
@@ -318,5 +318,29 @@ out:
return nread;
}
+CURLcode Curl_h1_req_write_head(struct httpreq *req, int http_minor,
+ struct dynbuf *dbuf)
+{
+ CURLcode result;
+
+ result = Curl_dyn_addf(dbuf, "%s %s%s%s%s HTTP/1.%d\r\n",
+ req->method,
+ req->scheme? req->scheme : "",
+ req->scheme? "://" : "",
+ req->authority? req->authority : "",
+ req->path? req->path : "",
+ http_minor);
+ if(result)
+ goto out;
+
+ result = Curl_dynhds_h1_dprint(&req->headers, dbuf);
+ if(result)
+ goto out;
+
+ result = Curl_dyn_addn(dbuf, STRCONST("\r\n"));
+
+out:
+ return result;
+}
#endif /* !CURL_DISABLE_HTTP */
diff --git a/Utilities/cmcurl/lib/http1.h b/Utilities/cmcurl/lib/http1.h
index b1eaa96..2de302f 100644
--- a/Utilities/cmcurl/lib/http1.h
+++ b/Utilities/cmcurl/lib/http1.h
@@ -56,6 +56,8 @@ ssize_t Curl_h1_req_parse_read(struct h1_req_parser *parser,
CURLcode Curl_h1_req_dprint(const struct httpreq *req,
struct dynbuf *dbuf);
+CURLcode Curl_h1_req_write_head(struct httpreq *req, int http_minor,
+ struct dynbuf *dbuf);
#endif /* !CURL_DISABLE_HTTP */
#endif /* HEADER_CURL_HTTP1_H */
diff --git a/Utilities/cmcurl/lib/http2.c b/Utilities/cmcurl/lib/http2.c
index e0cda76..c8b0594 100644
--- a/Utilities/cmcurl/lib/http2.c
+++ b/Utilities/cmcurl/lib/http2.c
@@ -1688,7 +1688,7 @@ static ssize_t http2_handle_stream_close(struct Curl_cfilter *cf,
"connection", stream->id);
connclose(cf->conn, "REFUSED_STREAM"); /* don't use this anymore */
data->state.refused_stream = TRUE;
- *err = CURLE_SEND_ERROR; /* trigger Curl_retry_request() later */
+ *err = CURLE_RECV_ERROR; /* trigger Curl_retry_request() later */
return -1;
}
else if(stream->error != NGHTTP2_NO_ERROR) {
@@ -2313,7 +2313,7 @@ out:
"h2 windows %d-%d (stream-conn), "
"buffers %zu-%zu (stream-conn)",
stream->id, len, nwritten, *err,
- (ssize_t)stream->upload_left,
+ stream->upload_left,
nghttp2_session_get_stream_remote_window_size(
ctx->h2, stream->id),
nghttp2_session_get_remote_window_size(ctx->h2),
@@ -2425,6 +2425,8 @@ static void cf_h2_close(struct Curl_cfilter *cf, struct Curl_easy *data)
cf_h2_ctx_clear(ctx);
CF_DATA_RESTORE(cf, save);
}
+ if(cf->next)
+ cf->next->cft->do_close(cf->next, data);
}
static void cf_h2_destroy(struct Curl_cfilter *cf, struct Curl_easy *data)
diff --git a/Utilities/cmcurl/lib/http_aws_sigv4.c b/Utilities/cmcurl/lib/http_aws_sigv4.c
index f39d02c..901c22f 100644
--- a/Utilities/cmcurl/lib/http_aws_sigv4.c
+++ b/Utilities/cmcurl/lib/http_aws_sigv4.c
@@ -34,6 +34,7 @@
#include "transfer.h"
#include "parsedate.h"
#include "sendf.h"
+#include "escape.h"
#include <time.h>
@@ -63,11 +64,8 @@
static void sha256_to_hex(char *dst, unsigned char *sha)
{
- int i;
-
- for(i = 0; i < SHA256_DIGEST_LENGTH; ++i) {
- msnprintf(dst + (i * 2), SHA256_HEX_LENGTH - (i * 2), "%02x", sha[i]);
- }
+ Curl_hexencode(sha, SHA256_DIGEST_LENGTH,
+ (unsigned char *)dst, SHA256_HEX_LENGTH);
}
static char *find_date_hdr(struct Curl_easy *data, const char *sig_hdr)
@@ -409,6 +407,11 @@ static int compare_func(const void *a, const void *b)
{
const struct pair *aa = a;
const struct pair *bb = b;
+ /* If one element is empty, the other is always sorted higher */
+ if(aa->len == 0)
+ return -1;
+ if(bb->len == 0)
+ return 1;
return strncmp(aa->p, bb->p, aa->len < bb->len ? aa->len : bb->len);
}
diff --git a/Utilities/cmcurl/lib/http_chunks.c b/Utilities/cmcurl/lib/http_chunks.c
index bda00d3..2a401d1 100644
--- a/Utilities/cmcurl/lib/http_chunks.c
+++ b/Utilities/cmcurl/lib/http_chunks.c
@@ -175,10 +175,7 @@ CHUNKcode Curl_httpchunk_read(struct Curl_easy *data,
/* Write the data portion available */
if(!data->set.http_te_skip && !k->ignorebody) {
- if(!data->set.http_ce_skip && k->writer_stack)
- result = Curl_unencode_write(data, k->writer_stack, datap, piece);
- else
- result = Curl_client_write(data, CLIENTWRITE_BODY, datap, piece);
+ result = Curl_client_write(data, CLIENTWRITE_BODY, datap, piece);
if(result) {
*extrap = result;
diff --git a/Utilities/cmcurl/lib/http_proxy.c b/Utilities/cmcurl/lib/http_proxy.c
index 60bbfbe..a1d6da9 100644
--- a/Utilities/cmcurl/lib/http_proxy.c
+++ b/Utilities/cmcurl/lib/http_proxy.c
@@ -52,6 +52,113 @@
#include "memdebug.h"
+CURLcode Curl_http_proxy_get_destination(struct Curl_cfilter *cf,
+ const char **phostname,
+ int *pport, bool *pipv6_ip)
+{
+ DEBUGASSERT(cf);
+ DEBUGASSERT(cf->conn);
+
+ if(cf->conn->bits.conn_to_host)
+ *phostname = cf->conn->conn_to_host.name;
+ else if(cf->sockindex == SECONDARYSOCKET)
+ *phostname = cf->conn->secondaryhostname;
+ else
+ *phostname = cf->conn->host.name;
+
+ if(cf->sockindex == SECONDARYSOCKET)
+ *pport = cf->conn->secondary_port;
+ else if(cf->conn->bits.conn_to_port)
+ *pport = cf->conn->conn_to_port;
+ else
+ *pport = cf->conn->remote_port;
+
+ if(*phostname != cf->conn->host.name)
+ *pipv6_ip = (strchr(*phostname, ':') != NULL);
+ else
+ *pipv6_ip = cf->conn->bits.ipv6_ip;
+
+ return CURLE_OK;
+}
+
+CURLcode Curl_http_proxy_create_CONNECT(struct httpreq **preq,
+ struct Curl_cfilter *cf,
+ struct Curl_easy *data,
+ int http_version_major)
+{
+ const char *hostname = NULL;
+ char *authority = NULL;
+ int port;
+ bool ipv6_ip;
+ CURLcode result;
+ struct httpreq *req = NULL;
+
+ result = Curl_http_proxy_get_destination(cf, &hostname, &port, &ipv6_ip);
+ if(result)
+ goto out;
+
+ authority = aprintf("%s%s%s:%d", ipv6_ip?"[":"", hostname,
+ ipv6_ip?"]":"", port);
+ if(!authority) {
+ result = CURLE_OUT_OF_MEMORY;
+ goto out;
+ }
+
+ result = Curl_http_req_make(&req, "CONNECT", sizeof("CONNECT")-1,
+ NULL, 0, authority, strlen(authority),
+ NULL, 0);
+ if(result)
+ goto out;
+
+ /* Setup the proxy-authorization header, if any */
+ result = Curl_http_output_auth(data, cf->conn, req->method, HTTPREQ_GET,
+ req->authority, TRUE);
+ if(result)
+ goto out;
+
+ /* If user is not overriding Host: header, we add for HTTP/1.x */
+ if(http_version_major == 1 &&
+ !Curl_checkProxyheaders(data, cf->conn, STRCONST("Host"))) {
+ result = Curl_dynhds_cadd(&req->headers, "Host", authority);
+ if(result)
+ goto out;
+ }
+
+ if(data->state.aptr.proxyuserpwd) {
+ result = Curl_dynhds_h1_cadd_line(&req->headers,
+ data->state.aptr.proxyuserpwd);
+ if(result)
+ goto out;
+ }
+
+ if(!Curl_checkProxyheaders(data, cf->conn, STRCONST("User-Agent"))
+ && data->set.str[STRING_USERAGENT]) {
+ result = Curl_dynhds_cadd(&req->headers, "User-Agent",
+ data->set.str[STRING_USERAGENT]);
+ if(result)
+ goto out;
+ }
+
+ if(http_version_major == 1 &&
+ !Curl_checkProxyheaders(data, cf->conn, STRCONST("Proxy-Connection"))) {
+ result = Curl_dynhds_cadd(&req->headers, "Proxy-Connection", "Keep-Alive");
+ if(result)
+ goto out;
+ }
+
+ result = Curl_dynhds_add_custom(data, TRUE, &req->headers);
+
+out:
+ if(result && req) {
+ Curl_http_req_free(req);
+ req = NULL;
+ }
+ free(authority);
+ *preq = req;
+ return result;
+}
+
+
struct cf_proxy_ctx {
/* the protocol specific sub-filter we install during connect */
struct Curl_cfilter *cf_protocol;
@@ -105,7 +212,6 @@ connect_sub:
break;
#endif
default:
- CURL_TRC_CF(data, cf, "installing subfilter for default HTTP/1.1");
infof(data, "CONNECT tunnel: unsupported ALPN(%d) negotiated", alpn);
result = CURLE_COULDNT_CONNECT;
goto out;
diff --git a/Utilities/cmcurl/lib/http_proxy.h b/Utilities/cmcurl/lib/http_proxy.h
index a1a0372..2b5f7ae 100644
--- a/Utilities/cmcurl/lib/http_proxy.h
+++ b/Utilities/cmcurl/lib/http_proxy.h
@@ -30,6 +30,15 @@
#include "urldata.h"
+CURLcode Curl_http_proxy_get_destination(struct Curl_cfilter *cf,
+ const char **phostname,
+ int *pport, bool *pipv6_ip);
+
+CURLcode Curl_http_proxy_create_CONNECT(struct httpreq **preq,
+ struct Curl_cfilter *cf,
+ struct Curl_easy *data,
+ int http_version_major);
+
/* Default proxy timeout in milliseconds */
#define PROXY_TIMEOUT (3600*1000)
diff --git a/Utilities/cmcurl/lib/idn.c b/Utilities/cmcurl/lib/idn.c
index 1f31a95..a024691 100644
--- a/Utilities/cmcurl/lib/idn.c
+++ b/Utilities/cmcurl/lib/idn.c
@@ -91,6 +91,8 @@ static CURLcode win32_idn_to_ascii(const char *in, char **out)
else
return CURLE_URL_MALFORMAT;
}
+ else
+ return CURLE_URL_MALFORMAT;
return CURLE_OK;
}
@@ -174,6 +176,9 @@ static CURLcode idn_decode(const char *input, char **output)
if(rc != IDN2_OK)
result = CURLE_URL_MALFORMAT;
}
+ else
+ /* a too old libidn2 version */
+ result = CURLE_NOT_BUILT_IN;
#elif defined(USE_WIN32_IDN)
result = win32_idn_to_ascii(input, &decoded);
#endif
diff --git a/Utilities/cmcurl/lib/inet_ntop.c b/Utilities/cmcurl/lib/inet_ntop.c
index 135f486..c9cee0c 100644
--- a/Utilities/cmcurl/lib/inet_ntop.c
+++ b/Utilities/cmcurl/lib/inet_ntop.c
@@ -96,10 +96,10 @@ static char *inet_ntop6 (const unsigned char *src, char *dst, size_t size)
char tmp[sizeof("ffff:ffff:ffff:ffff:ffff:ffff:255.255.255.255")];
char *tp;
struct {
- long base;
- long len;
+ int base;
+ int len;
} best, cur;
- unsigned long words[IN6ADDRSZ / INT16SZ];
+ unsigned int words[IN6ADDRSZ / INT16SZ];
int i;
/* Preprocess:
@@ -108,7 +108,7 @@ static char *inet_ntop6 (const unsigned char *src, char *dst, size_t size)
*/
memset(words, '\0', sizeof(words));
for(i = 0; i < IN6ADDRSZ; i++)
- words[i/2] |= (src[i] << ((1 - (i % 2)) << 3));
+ words[i/2] |= ((unsigned int)src[i] << ((1 - (i % 2)) << 3));
best.base = -1;
cur.base = -1;
@@ -159,7 +159,7 @@ static char *inet_ntop6 (const unsigned char *src, char *dst, size_t size)
tp += strlen(tp);
break;
}
- tp += msnprintf(tp, 5, "%lx", words[i]);
+ tp += msnprintf(tp, 5, "%x", words[i]);
}
/* Was it a trailing run of 0x00's?
diff --git a/Utilities/cmcurl/lib/ldap.c b/Utilities/cmcurl/lib/ldap.c
index 33a4dea..239d3fb 100644
--- a/Utilities/cmcurl/lib/ldap.c
+++ b/Utilities/cmcurl/lib/ldap.c
@@ -735,7 +735,9 @@ static CURLcode ldap_do(struct Curl_easy *data, bool *done)
if(result)
goto quit;
dlsize++;
- Curl_pgrsSetDownloadCounter(data, dlsize);
+ result = Curl_pgrsSetDownloadCounter(data, dlsize);
+ if(result)
+ goto quit;
}
if(ber)
diff --git a/Utilities/cmcurl/lib/mime.c b/Utilities/cmcurl/lib/mime.c
index 842b2da..3b27e59 100644
--- a/Utilities/cmcurl/lib/mime.c
+++ b/Utilities/cmcurl/lib/mime.c
@@ -1289,9 +1289,9 @@ curl_mime *curl_mime_init(struct Curl_easy *easy)
mime->lastpart = NULL;
memset(mime->boundary, '-', MIME_BOUNDARY_DASHES);
- if(Curl_rand_hex(easy,
- (unsigned char *) &mime->boundary[MIME_BOUNDARY_DASHES],
- MIME_RAND_BOUNDARY_CHARS + 1)) {
+ if(Curl_rand_alnum(easy,
+ (unsigned char *) &mime->boundary[MIME_BOUNDARY_DASHES],
+ MIME_RAND_BOUNDARY_CHARS + 1)) {
/* failed to get random separator, bail out */
free(mime);
return NULL;
diff --git a/Utilities/cmcurl/lib/mime.h b/Utilities/cmcurl/lib/mime.h
index 04adf2d..0a05c2a 100644
--- a/Utilities/cmcurl/lib/mime.h
+++ b/Utilities/cmcurl/lib/mime.h
@@ -27,7 +27,7 @@
#include "curl_setup.h"
#define MIME_BOUNDARY_DASHES 24 /* leading boundary dashes */
-#define MIME_RAND_BOUNDARY_CHARS 16 /* Nb. of random boundary chars. */
+#define MIME_RAND_BOUNDARY_CHARS 22 /* Nb. of random boundary chars. */
#define MAX_ENCODED_LINE_LENGTH 76 /* Maximum encoded line length. */
#define ENCODING_BUFFER_SIZE 256 /* Encoding temp buffers size. */
diff --git a/Utilities/cmcurl/lib/mqtt.c b/Utilities/cmcurl/lib/mqtt.c
index 30edf3d..54f8882 100644
--- a/Utilities/cmcurl/lib/mqtt.c
+++ b/Utilities/cmcurl/lib/mqtt.c
@@ -109,6 +109,7 @@ static CURLcode mqtt_setup_conn(struct Curl_easy *data,
mq = calloc(1, sizeof(struct MQTT));
if(!mq)
return CURLE_OUT_OF_MEMORY;
+ Curl_dyn_init(&mq->recvbuf, DYN_MQTT_RECV);
data->req.p.mqtt = mq;
return CURLE_OK;
}
@@ -295,12 +296,12 @@ static CURLcode mqtt_connect(struct Curl_easy *data)
/* set initial values for the CONNECT packet */
pos = init_connpack(packet, remain, remain_pos);
- result = Curl_rand_hex(data, (unsigned char *)&client_id[clen],
- MQTT_CLIENTID_LEN - clen + 1);
+ result = Curl_rand_alnum(data, (unsigned char *)&client_id[clen],
+ MQTT_CLIENTID_LEN - clen + 1);
/* add client id */
rc = add_client_id(client_id, strlen(client_id), packet, pos + 1);
if(rc) {
- failf(data, "Client ID length mismatched: [%lu]", strlen(client_id));
+ failf(data, "Client ID length mismatched: [%zu]", strlen(client_id));
result = CURLE_WEIRD_SERVER_REPLY;
goto end;
}
@@ -317,7 +318,7 @@ static CURLcode mqtt_connect(struct Curl_easy *data)
rc = add_user(username, ulen,
(unsigned char *)packet, start_user, remain_pos);
if(rc) {
- failf(data, "Username is too large: [%lu]", ulen);
+ failf(data, "Username is too large: [%zu]", ulen);
result = CURLE_WEIRD_SERVER_REPLY;
goto end;
}
@@ -327,7 +328,7 @@ static CURLcode mqtt_connect(struct Curl_easy *data)
if(plen) {
rc = add_passwd(passwd, plen, packet, start_pwd, remain_pos);
if(rc) {
- failf(data, "Password is too large: [%lu]", plen);
+ failf(data, "Password is too large: [%zu]", plen);
result = CURLE_WEIRD_SERVER_REPLY;
goto end;
}
@@ -350,36 +351,66 @@ static CURLcode mqtt_disconnect(struct Curl_easy *data)
struct MQTT *mq = data->req.p.mqtt;
result = mqtt_send(data, (char *)"\xe0\x00", 2);
Curl_safefree(mq->sendleftovers);
+ Curl_dyn_free(&mq->recvbuf);
return result;
}
-static CURLcode mqtt_verify_connack(struct Curl_easy *data)
+static CURLcode mqtt_recv_atleast(struct Curl_easy *data, size_t nbytes)
{
+ struct MQTT *mq = data->req.p.mqtt;
+ size_t rlen = Curl_dyn_len(&mq->recvbuf);
CURLcode result;
- struct connectdata *conn = data->conn;
- curl_socket_t sockfd = conn->sock[FIRSTSOCKET];
- unsigned char readbuf[MQTT_CONNACK_LEN];
- ssize_t nread;
- result = Curl_read(data, sockfd, (char *)readbuf, MQTT_CONNACK_LEN, &nread);
- if(result)
- goto fail;
+ if(rlen < nbytes) {
+ unsigned char readbuf[1024];
+ ssize_t nread;
- Curl_debug(data, CURLINFO_HEADER_IN, (char *)readbuf, (size_t)nread);
+ DEBUGASSERT(nbytes - rlen < sizeof(readbuf));
+ result = Curl_read(data, data->conn->sock[FIRSTSOCKET],
+ (char *)readbuf, nbytes - rlen, &nread);
+ if(result)
+ return result;
+ DEBUGASSERT(nread >= 0);
+ if(Curl_dyn_addn(&mq->recvbuf, readbuf, (size_t)nread))
+ return CURLE_OUT_OF_MEMORY;
+ rlen = Curl_dyn_len(&mq->recvbuf);
+ }
+ return (rlen >= nbytes)? CURLE_OK : CURLE_AGAIN;
+}
- /* fixme */
- if(nread < MQTT_CONNACK_LEN) {
- result = CURLE_WEIRD_SERVER_REPLY;
+static void mqtt_recv_consume(struct Curl_easy *data, size_t nbytes)
+{
+ struct MQTT *mq = data->req.p.mqtt;
+ size_t rlen = Curl_dyn_len(&mq->recvbuf);
+ if(rlen <= nbytes)
+ Curl_dyn_reset(&mq->recvbuf);
+ else
+ Curl_dyn_tail(&mq->recvbuf, rlen - nbytes);
+}
+
+static CURLcode mqtt_verify_connack(struct Curl_easy *data)
+{
+ struct MQTT *mq = data->req.p.mqtt;
+ CURLcode result;
+ char *ptr;
+
+ result = mqtt_recv_atleast(data, MQTT_CONNACK_LEN);
+ if(result)
goto fail;
- }
/* verify CONNACK */
- if(readbuf[0] != 0x00 || readbuf[1] != 0x00) {
+ DEBUGASSERT(Curl_dyn_len(&mq->recvbuf) >= MQTT_CONNACK_LEN);
+ ptr = Curl_dyn_ptr(&mq->recvbuf);
+ Curl_debug(data, CURLINFO_HEADER_IN, ptr, MQTT_CONNACK_LEN);
+
+ if(ptr[0] != 0x00 || ptr[1] != 0x00) {
failf(data, "Expected %02x%02x but got %02x%02x",
- 0x00, 0x00, readbuf[0], readbuf[1]);
+ 0x00, 0x00, ptr[0], ptr[1]);
+ Curl_dyn_reset(&mq->recvbuf);
result = CURLE_WEIRD_SERVER_REPLY;
+ goto fail;
}
-
+ mqtt_recv_consume(data, MQTT_CONNACK_LEN);
fail:
return result;
}
@@ -452,31 +483,29 @@ fail:
*/
static CURLcode mqtt_verify_suback(struct Curl_easy *data)
{
- CURLcode result;
+ struct MQTT *mq = data->req.p.mqtt;
struct connectdata *conn = data->conn;
- curl_socket_t sockfd = conn->sock[FIRSTSOCKET];
- unsigned char readbuf[MQTT_SUBACK_LEN];
- ssize_t nread;
struct mqtt_conn *mqtt = &conn->proto.mqtt;
+ CURLcode result;
+ char *ptr;
- result = Curl_read(data, sockfd, (char *)readbuf, MQTT_SUBACK_LEN, &nread);
+ result = mqtt_recv_atleast(data, MQTT_SUBACK_LEN);
if(result)
goto fail;
- Curl_debug(data, CURLINFO_HEADER_IN, (char *)readbuf, (size_t)nread);
-
- /* fixme */
- if(nread < MQTT_SUBACK_LEN) {
+ /* verify SUBACK */
+ DEBUGASSERT(Curl_dyn_len(&mq->recvbuf) >= MQTT_SUBACK_LEN);
+ ptr = Curl_dyn_ptr(&mq->recvbuf);
+ Curl_debug(data, CURLINFO_HEADER_IN, ptr, MQTT_SUBACK_LEN);
+
+ if(((unsigned char)ptr[0]) != ((mqtt->packetid >> 8) & 0xff) ||
+ ((unsigned char)ptr[1]) != (mqtt->packetid & 0xff) ||
+ ptr[2] != 0x00) {
+ Curl_dyn_reset(&mq->recvbuf);
result = CURLE_WEIRD_SERVER_REPLY;
goto fail;
}
-
- /* verify SUBACK */
- if(readbuf[0] != ((mqtt->packetid >> 8) & 0xff) ||
- readbuf[1] != (mqtt->packetid & 0xff) ||
- readbuf[2] != 0x00)
- result = CURLE_WEIRD_SERVER_REPLY;
-
+ mqtt_recv_consume(data, MQTT_SUBACK_LEN);
fail:
return result;
}
@@ -668,7 +697,9 @@ MQTT_SUBACK_COMING:
mq->npacket -= nread;
k->bytecount += nread;
- Curl_pgrsSetDownloadCounter(data, k->bytecount);
+ result = Curl_pgrsSetDownloadCounter(data, k->bytecount);
+ if(result)
+ goto end;
/* if QoS is set, message contains packet id */
@@ -711,6 +742,7 @@ static CURLcode mqtt_done(struct Curl_easy *data,
(void)status;
(void)premature;
Curl_safefree(mq->sendleftovers);
+ Curl_dyn_free(&mq->recvbuf);
return CURLE_OK;
}
diff --git a/Utilities/cmcurl/lib/mqtt.h b/Utilities/cmcurl/lib/mqtt.h
index 6396136..84f1770 100644
--- a/Utilities/cmcurl/lib/mqtt.h
+++ b/Utilities/cmcurl/lib/mqtt.h
@@ -56,6 +56,7 @@ struct MQTT {
size_t npacket; /* byte counter */
unsigned char firstbyte;
size_t remaining_length;
+ struct dynbuf recvbuf;
};
#endif /* HEADER_CURL_MQTT_H */
diff --git a/Utilities/cmcurl/lib/multi.c b/Utilities/cmcurl/lib/multi.c
index bb57dbc..ff753ac 100644
--- a/Utilities/cmcurl/lib/multi.c
+++ b/Utilities/cmcurl/lib/multi.c
@@ -665,7 +665,6 @@ static CURLcode multi_done(struct Curl_easy *data,
{
CURLcode result;
struct connectdata *conn = data->conn;
- unsigned int i;
#if defined(DEBUGBUILD) && !defined(CURL_DISABLE_VERBOSE_STRINGS)
DEBUGF(infof(data, "multi_done[%s]: status: %d prem: %d done: %d",
@@ -721,12 +720,7 @@ static CURLcode multi_done(struct Curl_easy *data,
Curl_safefree(data->state.ulbuf);
- /* if the transfer was completed in a paused state there can be buffered
- data left to free */
- for(i = 0; i < data->state.tempcount; i++) {
- Curl_dyn_free(&data->state.tempwrite[i].b);
- }
- data->state.tempcount = 0;
+ Curl_client_cleanup(data);
CONNCACHE_LOCK(data);
Curl_detach_connection(data);
@@ -2131,9 +2125,11 @@ static CURLMcode multi_runsingle(struct Curl_multi *multi,
}
if(!result)
result = protocol_connect(data, &protocol_connected);
- if(!result && !protocol_connected)
+ if(!result && !protocol_connected) {
/* switch to waiting state */
multistate(data, MSTATE_PROTOCONNECTING);
+ rc = CURLM_CALL_MULTI_PERFORM;
+ }
else if(!result) {
/* protocol connect has completed, go WAITDO or DO */
multistate(data, MSTATE_DO);
@@ -2220,6 +2216,7 @@ static CURLMcode multi_runsingle(struct Curl_multi *multi,
/* DO was not completed in one function call, we must continue
DOING... */
multistate(data, MSTATE_DOING);
+ rc = CURLM_CALL_MULTI_PERFORM;
}
/* after DO, go DO_DONE... or DO_MORE */
@@ -2227,6 +2224,7 @@ static CURLMcode multi_runsingle(struct Curl_multi *multi,
/* we're supposed to do more, but we need to sit down, relax
and wait a little while first */
multistate(data, MSTATE_DOING_MORE);
+ rc = CURLM_CALL_MULTI_PERFORM;
}
else {
/* we're done with the DO, now DID */
@@ -3139,7 +3137,7 @@ static CURLMcode add_next_timeout(struct curltime now,
struct Curl_llist_element *n = e->next;
timediff_t diff;
node = (struct time_node *)e->ptr;
- diff = Curl_timediff(node->time, now);
+ diff = Curl_timediff_us(node->time, now);
if(diff <= 0)
/* remove outdated entry */
Curl_llist_remove(list, e, NULL);
@@ -3422,20 +3420,10 @@ static CURLMcode multi_timeout(struct Curl_multi *multi,
if(Curl_splaycomparekeys(multi->timetree->key, now) > 0) {
/* some time left before expiration */
- timediff_t diff = Curl_timediff(multi->timetree->key, now);
- if(diff <= 0)
- /*
- * Since we only provide millisecond resolution on the returned value
- * and the diff might be less than one millisecond here, we don't
- * return zero as that may cause short bursts of busyloops on fast
- * processors while the diff is still present but less than one
- * millisecond! instead we return 1 until the time is ripe.
- */
- *timeout_ms = 1;
- else
- /* this should be safe even on 64 bit archs, as we don't use that
- overly long timeouts */
- *timeout_ms = (long)diff;
+ timediff_t diff = Curl_timediff_ceil(multi->timetree->key, now);
+ /* this should be safe even on 32 bit archs, as we don't use that
+ overly long timeouts */
+ *timeout_ms = (long)diff;
}
else
/* 0 means immediately */
@@ -3783,41 +3771,26 @@ bool Curl_is_in_callback(struct Curl_easy *easy)
(easy->multi_easy && easy->multi_easy->in_callback));
}
-#ifdef DEBUGBUILD
-void Curl_multi_dump(struct Curl_multi *multi)
-{
- struct Curl_easy *data;
- int i;
- fprintf(stderr, "* Multi status: %d handles, %d alive\n",
- multi->num_easy, multi->num_alive);
- for(data = multi->easyp; data; data = data->next) {
- if(data->mstate < MSTATE_COMPLETED) {
- /* only display handles that are not completed */
- fprintf(stderr, "handle %p, state %s, %d sockets\n",
- (void *)data,
- multi_statename[data->mstate], data->numsocks);
- for(i = 0; i < data->numsocks; i++) {
- curl_socket_t s = data->sockets[i];
- struct Curl_sh_entry *entry = sh_getentry(&multi->sockhash, s);
-
- fprintf(stderr, "%d ", (int)s);
- if(!entry) {
- fprintf(stderr, "INTERNAL CONFUSION\n");
- continue;
- }
- fprintf(stderr, "[%s %s] ",
- (entry->action&CURL_POLL_IN)?"RECVING":"",
- (entry->action&CURL_POLL_OUT)?"SENDING":"");
- }
- if(data->numsocks)
- fprintf(stderr, "\n");
- }
- }
-}
-#endif
-
unsigned int Curl_multi_max_concurrent_streams(struct Curl_multi *multi)
{
DEBUGASSERT(multi);
return multi->max_concurrent_streams;
}
+
+struct Curl_easy **curl_multi_get_handles(struct Curl_multi *multi)
+{
+ struct Curl_easy **a = malloc(sizeof(struct Curl_easy *) *
+ (multi->num_easy + 1));
+ if(a) {
+ int i = 0;
+ struct Curl_easy *e = multi->easyp;
+ while(e) {
+ DEBUGASSERT(i < multi->num_easy);
+ if(!e->internal)
+ a[i++] = e;
+ e = e->next;
+ }
+ a[i] = NULL; /* last entry is a NULL */
+ }
+ return a;
+}
diff --git a/Utilities/cmcurl/lib/multiif.h b/Utilities/cmcurl/lib/multiif.h
index 7f08ecc..7a344fa 100644
--- a/Utilities/cmcurl/lib/multiif.h
+++ b/Utilities/cmcurl/lib/multiif.h
@@ -62,15 +62,6 @@ struct Curl_multi *Curl_multi_handle(int hashsize, int chashsize,
/* mask for checking if read and/or write is set for index x */
#define GETSOCK_MASK_RW(x) (GETSOCK_READSOCK(x)|GETSOCK_WRITESOCK(x))
-#ifdef DEBUGBUILD
- /*
- * Curl_multi_dump is not a stable public function, this is only meant to
- * allow easier tracking of the internal handle's state and what sockets
- * they use. Only for research and development DEBUGBUILD enabled builds.
- */
-void Curl_multi_dump(struct Curl_multi *multi);
-#endif
-
/* Return the value of the CURLMOPT_MAX_HOST_CONNECTIONS option */
size_t Curl_multi_max_host_connections(struct Curl_multi *multi);
diff --git a/Utilities/cmcurl/lib/openldap.c b/Utilities/cmcurl/lib/openldap.c
index 41fecf9..3aff306 100644
--- a/Utilities/cmcurl/lib/openldap.c
+++ b/Utilities/cmcurl/lib/openldap.c
@@ -199,11 +199,11 @@ struct ldapreqinfo {
};
/*
- * state()
+ * oldap_state()
*
* This is the ONLY way to change LDAP state!
*/
-static void state(struct Curl_easy *data, ldapstate newstate)
+static void oldap_state(struct Curl_easy *data, ldapstate newstate)
{
struct ldapconninfo *ldapc = data->conn->proto.ldapc;
@@ -444,7 +444,7 @@ static CURLcode oldap_perform_bind(struct Curl_easy *data, ldapstate newstate)
rc = ldap_sasl_bind(li->ld, binddn, LDAP_SASL_SIMPLE, &passwd,
NULL, NULL, &li->msgid);
if(rc == LDAP_SUCCESS)
- state(data, newstate);
+ oldap_state(data, newstate);
else
result = oldap_map_error(rc,
data->state.aptr.user?
@@ -467,7 +467,7 @@ static CURLcode oldap_perform_mechs(struct Curl_easy *data)
(char **) supportedSASLMechanisms, 0,
NULL, NULL, NULL, 0, &li->msgid);
if(rc == LDAP_SUCCESS)
- state(data, OLDAP_MECHS);
+ oldap_state(data, OLDAP_MECHS);
else
result = oldap_map_error(rc, CURLE_LOGIN_DENIED);
return result;
@@ -480,7 +480,7 @@ static CURLcode oldap_perform_sasl(struct Curl_easy *data)
struct ldapconninfo *li = data->conn->proto.ldapc;
CURLcode result = Curl_sasl_start(&li->sasl, data, TRUE, &progress);
- state(data, OLDAP_SASL);
+ oldap_state(data, OLDAP_SASL);
if(!result && progress != SASL_INPROGRESS)
result = CURLE_LOGIN_DENIED;
return result;
@@ -503,7 +503,7 @@ static CURLcode oldap_ssl_connect(struct Curl_easy *data, ldapstate newstate)
result = Curl_conn_connect(data, FIRSTSOCKET, FALSE, &ssldone);
if(!result) {
- state(data, newstate);
+ oldap_state(data, newstate);
if(ssldone) {
Sockbuf *sb;
@@ -527,7 +527,7 @@ static CURLcode oldap_perform_starttls(struct Curl_easy *data)
int rc = ldap_start_tls(li->ld, NULL, NULL, &li->msgid);
if(rc == LDAP_SUCCESS)
- state(data, OLDAP_STARTTLS);
+ oldap_state(data, OLDAP_STARTTLS);
else
result = oldap_map_error(rc, CURLE_USE_SSL_FAILED);
return result;
@@ -682,7 +682,7 @@ static CURLcode oldap_state_sasl_resp(struct Curl_easy *data,
else {
result = Curl_sasl_continue(&li->sasl, data, code, &progress);
if(!result && progress != SASL_INPROGRESS)
- state(data, OLDAP_STOP);
+ oldap_state(data, OLDAP_STOP);
}
if(li->servercred)
@@ -710,7 +710,7 @@ static CURLcode oldap_state_bind_resp(struct Curl_easy *data, LDAPMessage *msg,
result = oldap_map_error(rc, CURLE_LDAP_CANNOT_BIND);
}
else
- state(data, OLDAP_STOP);
+ oldap_state(data, OLDAP_STOP);
if(bv)
ber_bvfree(bv);
@@ -804,7 +804,8 @@ static CURLcode oldap_connecting(struct Curl_easy *data, bool *done)
else if(data->state.aptr.user)
result = oldap_perform_bind(data, OLDAP_BIND);
else {
- state(data, OLDAP_STOP); /* Version 3 supported: no bind required */
+ /* Version 3 supported: no bind required */
+ oldap_state(data, OLDAP_STOP);
result = CURLE_OK;
}
}
diff --git a/Utilities/cmcurl/lib/pingpong.c b/Utilities/cmcurl/lib/pingpong.c
index 136985f..0081c9c 100644
--- a/Utilities/cmcurl/lib/pingpong.c
+++ b/Utilities/cmcurl/lib/pingpong.c
@@ -361,7 +361,7 @@ CURLcode Curl_pp_readresp(struct Curl_easy *data,
* for "headers". The response lines can be seen as a kind of
* headers.
*/
- result = Curl_client_write(data, CLIENTWRITE_HEADER,
+ result = Curl_client_write(data, CLIENTWRITE_INFO,
pp->linestart_resp, perline);
if(result)
return result;
diff --git a/Utilities/cmcurl/lib/progress.c b/Utilities/cmcurl/lib/progress.c
index 6092b78..e783a9c 100644
--- a/Utilities/cmcurl/lib/progress.c
+++ b/Utilities/cmcurl/lib/progress.c
@@ -317,9 +317,16 @@ timediff_t Curl_pgrsLimitWaitTime(curl_off_t cursize,
/*
* Set the number of downloaded bytes so far.
*/
-void Curl_pgrsSetDownloadCounter(struct Curl_easy *data, curl_off_t size)
+CURLcode Curl_pgrsSetDownloadCounter(struct Curl_easy *data, curl_off_t size)
{
+ if(data->set.max_filesize && (size > data->set.max_filesize)) {
+ failf(data, "Exceeded the maximum allowed file size "
+ "(%" CURL_FORMAT_CURL_OFF_T ")",
+ data->set.max_filesize);
+ return CURLE_FILESIZE_EXCEEDED;
+ }
data->progress.downloaded = size;
+ return CURLE_OK;
}
/*
diff --git a/Utilities/cmcurl/lib/progress.h b/Utilities/cmcurl/lib/progress.h
index 0049cd0..fc39e34 100644
--- a/Utilities/cmcurl/lib/progress.h
+++ b/Utilities/cmcurl/lib/progress.h
@@ -46,7 +46,10 @@ int Curl_pgrsDone(struct Curl_easy *data);
void Curl_pgrsStartNow(struct Curl_easy *data);
void Curl_pgrsSetDownloadSize(struct Curl_easy *data, curl_off_t size);
void Curl_pgrsSetUploadSize(struct Curl_easy *data, curl_off_t size);
-void Curl_pgrsSetDownloadCounter(struct Curl_easy *data, curl_off_t size);
+
+/* It is fine to not check the return code if 'size' is set to 0 */
+CURLcode Curl_pgrsSetDownloadCounter(struct Curl_easy *data, curl_off_t size);
+
void Curl_pgrsSetUploadCounter(struct Curl_easy *data, curl_off_t size);
void Curl_ratelimit(struct Curl_easy *data, struct curltime now);
int Curl_pgrsUpdate(struct Curl_easy *data);
diff --git a/Utilities/cmcurl/lib/rand.c b/Utilities/cmcurl/lib/rand.c
index a5620ea..6bd9613 100644
--- a/Utilities/cmcurl/lib/rand.c
+++ b/Utilities/cmcurl/lib/rand.c
@@ -24,6 +24,8 @@
#include "curl_setup.h"
+#include <limits.h>
+
#ifdef HAVE_FCNTL_H
#include <fcntl.h>
#endif
@@ -41,6 +43,7 @@ uint32_t arc4random(void);
#include "sendf.h"
#include "timeval.h"
#include "rand.h"
+#include "escape.h"
/* The last 3 #include files should be in this order */
#include "curl_printf.h"
@@ -49,12 +52,7 @@ uint32_t arc4random(void);
#ifdef WIN32
-#if defined(__MINGW32__) && !defined(__MINGW64_VERSION_MAJOR)
-# define HAVE_MINGW_ORIGINAL
-#endif
-
-#if defined(_WIN32_WINNT) && _WIN32_WINNT >= 0x600 && \
- !defined(HAVE_MINGW_ORIGINAL)
+#if defined(_WIN32_WINNT) && _WIN32_WINNT >= 0x600
# define HAVE_WIN_BCRYPTGENRANDOM
# include <bcrypt.h>
# ifdef _MSC_VER
@@ -234,9 +232,7 @@ CURLcode Curl_rand_hex(struct Curl_easy *data, unsigned char *rnd,
size_t num)
{
CURLcode result = CURLE_BAD_FUNCTION_ARGUMENT;
- const char *hex = "0123456789abcdef";
unsigned char buffer[128];
- unsigned char *bufp = buffer;
DEBUGASSERT(num > 1);
#ifdef __clang_analyzer__
@@ -255,13 +251,37 @@ CURLcode Curl_rand_hex(struct Curl_easy *data, unsigned char *rnd,
if(result)
return result;
+ Curl_hexencode(buffer, num/2, rnd, num + 1);
+ return result;
+}
+
+/*
+ * Curl_rand_alnum() fills the 'rnd' buffer with a given 'num' size with random
+ * alphanumerical chars PLUS a null-terminating byte.
+ */
+
+static const char alnum[] =
+ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
+
+CURLcode Curl_rand_alnum(struct Curl_easy *data, unsigned char *rnd,
+ size_t num)
+{
+ CURLcode result = CURLE_OK;
+ const int alnumspace = sizeof(alnum) - 1;
+ unsigned int r;
+ DEBUGASSERT(num > 1);
+
+ num--; /* save one for null-termination */
+
while(num) {
- /* clang-tidy warns on this line without this comment: */
- /* NOLINTNEXTLINE(clang-analyzer-core.UndefinedBinaryOperatorResult) */
- *rnd++ = hex[(*bufp & 0xF0)>>4];
- *rnd++ = hex[*bufp & 0x0F];
- bufp++;
- num -= 2;
+ do {
+ result = randit(data, &r);
+ if(result)
+ return result;
+ } while(r >= (UINT_MAX - UINT_MAX % alnumspace));
+
+ *rnd++ = alnum[r % alnumspace];
+ num--;
}
*rnd = 0;
diff --git a/Utilities/cmcurl/lib/rand.h b/Utilities/cmcurl/lib/rand.h
index 45ce3e7..1d009f5 100644
--- a/Utilities/cmcurl/lib/rand.h
+++ b/Utilities/cmcurl/lib/rand.h
@@ -34,6 +34,13 @@ CURLcode Curl_rand(struct Curl_easy *data, unsigned char *rnd, size_t num);
CURLcode Curl_rand_hex(struct Curl_easy *data, unsigned char *rnd,
size_t num);
+/*
+ * Curl_rand_alnum() fills the 'rnd' buffer with a given 'num' size with random
+ * alphanumerical chars PLUS a null-terminating byte.
+ */
+CURLcode Curl_rand_alnum(struct Curl_easy *data, unsigned char *rnd,
+ size_t num);
+
#ifdef WIN32
/* Random generator shared between the Schannel vtls and Curl_rand*()
functions */
diff --git a/Utilities/cmcurl/lib/sendf.c b/Utilities/cmcurl/lib/sendf.c
index d79ad08..0482c5d 100644
--- a/Utilities/cmcurl/lib/sendf.c
+++ b/Utilities/cmcurl/lib/sendf.c
@@ -40,6 +40,7 @@
#include "sendf.h"
#include "cfilters.h"
#include "connect.h"
+#include "content_encoding.h"
#include "vtls/vtls.h"
#include "vssh/ssh.h"
#include "easyif.h"
@@ -213,6 +214,7 @@ CURLcode Curl_write(struct Curl_easy *data,
static CURLcode pausewrite(struct Curl_easy *data,
int type, /* what type of data */
+ bool paused_body,
const char *ptr,
size_t len)
{
@@ -228,7 +230,8 @@ static CURLcode pausewrite(struct Curl_easy *data,
if(s->tempcount) {
for(i = 0; i< s->tempcount; i++) {
- if(s->tempwrite[i].type == type) {
+ if(s->tempwrite[i].type == type &&
+ !!s->tempwrite[i].paused_body == !!paused_body) {
/* data for this type exists */
newtype = FALSE;
break;
@@ -246,6 +249,7 @@ static CURLcode pausewrite(struct Curl_easy *data,
/* store this information in the state struct for later use */
Curl_dyn_init(&s->tempwrite[i].b, DYN_PAUSE_BUFFER);
s->tempwrite[i].type = type;
+ s->tempwrite[i].paused_body = paused_body;
s->tempcount++;
}
@@ -265,6 +269,7 @@ static CURLcode pausewrite(struct Curl_easy *data,
*/
static CURLcode chop_write(struct Curl_easy *data,
int type,
+ bool skip_body_write,
char *optr,
size_t olen)
{
@@ -281,10 +286,12 @@ static CURLcode chop_write(struct Curl_easy *data,
/* If reading is paused, append this data to the already held data for this
type. */
if(data->req.keepon & KEEP_RECV_PAUSE)
- return pausewrite(data, type, ptr, len);
+ return pausewrite(data, type, !skip_body_write, ptr, len);
/* Determine the callback(s) to use. */
- if(type & CLIENTWRITE_BODY) {
+ if(!skip_body_write &&
+ ((type & CLIENTWRITE_BODY) ||
+ ((type & CLIENTWRITE_HEADER) && data->set.include_header))) {
#ifdef USE_WEBSOCKETS
if(conn->handler->protocol & (CURLPROTO_WS|CURLPROTO_WSS)) {
writebody = Curl_ws_writecb;
@@ -294,7 +301,7 @@ static CURLcode chop_write(struct Curl_easy *data,
#endif
writebody = data->set.fwrite_func;
}
- if((type & CLIENTWRITE_HEADER) &&
+ if((type & (CLIENTWRITE_HEADER|CLIENTWRITE_INFO)) &&
(data->set.fwrite_header || data->set.writeheader)) {
/*
* Write headers to the same callback or to the especially setup
@@ -322,7 +329,7 @@ static CURLcode chop_write(struct Curl_easy *data,
failf(data, "Write callback asked for PAUSE when not supported");
return CURLE_WRITE_ERROR;
}
- return pausewrite(data, type, ptr, len);
+ return pausewrite(data, type, TRUE, ptr, len);
}
if(wrote != chunklen) {
failf(data, "Failure writing output to destination");
@@ -357,13 +364,7 @@ static CURLcode chop_write(struct Curl_easy *data,
Curl_set_in_callback(data, false);
if(CURL_WRITEFUNC_PAUSE == wrote)
- /* here we pass in the HEADER bit only since if this was body as well
- then it was passed already and clearly that didn't trigger the
- pause, so this is saved for later with the HEADER bit only */
- return pausewrite(data, CLIENTWRITE_HEADER |
- (type & (CLIENTWRITE_STATUS|CLIENTWRITE_CONNECT|
- CLIENTWRITE_1XX|CLIENTWRITE_TRAILER)),
- optr, olen);
+ return pausewrite(data, type, FALSE, optr, olen);
if(wrote != olen) {
failf(data, "Failed writing header");
return CURLE_WRITE_ERROR;
@@ -397,9 +398,187 @@ CURLcode Curl_client_write(struct Curl_easy *data,
len = convert_lineends(data, ptr, len);
}
#endif
- return chop_write(data, type, ptr, len);
+ /* it is one of those, at least */
+ DEBUGASSERT(type & (CLIENTWRITE_BODY|CLIENTWRITE_HEADER|CLIENTWRITE_INFO));
+ /* BODY is only BODY */
+ DEBUGASSERT(!(type & CLIENTWRITE_BODY) || (type == CLIENTWRITE_BODY));
+ /* INFO is only INFO */
+ DEBUGASSERT(!(type & CLIENTWRITE_INFO) || (type == CLIENTWRITE_INFO));
+
+ if(type == CLIENTWRITE_BODY) {
+ if(data->req.ignorebody)
+ return CURLE_OK;
+
+ if(data->req.writer_stack && !data->set.http_ce_skip)
+ return Curl_unencode_write(data, data->req.writer_stack, ptr, len);
+ }
+ return chop_write(data, type, FALSE, ptr, len);
+}
+
+CURLcode Curl_client_unpause(struct Curl_easy *data)
+{
+ CURLcode result = CURLE_OK;
+
+ if(data->state.tempcount) {
+ /* there are buffers for sending that can be delivered as the receive
+ pausing is lifted! */
+ unsigned int i;
+ unsigned int count = data->state.tempcount;
+ struct tempbuf writebuf[3]; /* there can only be three */
+
+ /* copy the structs to allow for immediate re-pausing */
+ for(i = 0; i < data->state.tempcount; i++) {
+ writebuf[i] = data->state.tempwrite[i];
+ Curl_dyn_init(&data->state.tempwrite[i].b, DYN_PAUSE_BUFFER);
+ }
+ data->state.tempcount = 0;
+
+ for(i = 0; i < count; i++) {
+ /* even if one function returns error, this loops through and frees
+ all buffers */
+ if(!result)
+ result = chop_write(data, writebuf[i].type,
+ !writebuf[i].paused_body,
+ Curl_dyn_ptr(&writebuf[i].b),
+ Curl_dyn_len(&writebuf[i].b));
+ Curl_dyn_free(&writebuf[i].b);
+ }
+ }
+ return result;
}
+void Curl_client_cleanup(struct Curl_easy *data)
+{
+ struct contenc_writer *writer = data->req.writer_stack;
+ size_t i;
+
+ while(writer) {
+ data->req.writer_stack = writer->downstream;
+ writer->handler->close_writer(data, writer);
+ free(writer);
+ writer = data->req.writer_stack;
+ }
+
+ for(i = 0; i < data->state.tempcount; i++) {
+ Curl_dyn_free(&data->state.tempwrite[i].b);
+ }
+ data->state.tempcount = 0;
+
+}
+
+/* Real client writer: no downstream. */
+static CURLcode client_cew_init(struct Curl_easy *data,
+ struct contenc_writer *writer)
+{
+ (void) data;
+ (void)writer;
+ return CURLE_OK;
+}
+
+static CURLcode client_cew_write(struct Curl_easy *data,
+ struct contenc_writer *writer,
+ const char *buf, size_t nbytes)
+{
+ (void)writer;
+ if(!nbytes || data->req.ignorebody)
+ return CURLE_OK;
+ return chop_write(data, CLIENTWRITE_BODY, FALSE, (char *)buf, nbytes);
+}
+
+static void client_cew_close(struct Curl_easy *data,
+ struct contenc_writer *writer)
+{
+ (void) data;
+ (void) writer;
+}
+
+static const struct content_encoding client_cew = {
+ NULL,
+ NULL,
+ client_cew_init,
+ client_cew_write,
+ client_cew_close,
+ sizeof(struct contenc_writer)
+};
+
+/* Create an unencoding writer stage using the given handler. */
+CURLcode Curl_client_create_writer(struct contenc_writer **pwriter,
+ struct Curl_easy *data,
+ const struct content_encoding *ce_handler,
+ int order)
+{
+ struct contenc_writer *writer;
+ CURLcode result = CURLE_OUT_OF_MEMORY;
+
+ DEBUGASSERT(ce_handler->writersize >= sizeof(struct contenc_writer));
+ writer = (struct contenc_writer *) calloc(1, ce_handler->writersize);
+ if(!writer)
+ goto out;
+
+ writer->handler = ce_handler;
+ writer->order = order;
+ result = ce_handler->init_writer(data, writer);
+
+out:
+ *pwriter = result? NULL : writer;
+ if(result)
+ free(writer);
+ return result;
+}
+
+void Curl_client_free_writer(struct Curl_easy *data,
+ struct contenc_writer *writer)
+{
+ if(writer) {
+ writer->handler->close_writer(data, writer);
+ free(writer);
+ }
+}
+
+/* allow no more than 5 "chained" compression steps */
+#define MAX_ENCODE_STACK 5
+
+
+static CURLcode init_writer_stack(struct Curl_easy *data)
+{
+ DEBUGASSERT(!data->req.writer_stack);
+ return Curl_client_create_writer(&data->req.writer_stack,
+ data, &client_cew, 0);
+}
+
+CURLcode Curl_client_add_writer(struct Curl_easy *data,
+ struct contenc_writer *writer)
+{
+ CURLcode result;
+
+ if(!data->req.writer_stack) {
+ result = init_writer_stack(data);
+ if(result)
+ return result;
+ }
+
+ if(data->req.writer_stack_depth++ >= MAX_ENCODE_STACK) {
+ failf(data, "Reject response due to more than %u content encodings",
+ MAX_ENCODE_STACK);
+ return CURLE_BAD_CONTENT_ENCODING;
+ }
+
+ /* Stack the unencoding stage. */
+ if(writer->order >= data->req.writer_stack->order) {
+ writer->downstream = data->req.writer_stack;
+ data->req.writer_stack = writer;
+ }
+ else {
+ struct contenc_writer *w = data->req.writer_stack;
+ while(w->downstream && writer->order < w->downstream->order)
+ w = w->downstream;
+ writer->downstream = w->downstream;
+ w->downstream = writer;
+ }
+ return CURLE_OK;
+}
+
+
/*
* Internal read-from-socket function. This is meant to deal with plain
* sockets, SSL sockets and kerberos sockets.
diff --git a/Utilities/cmcurl/lib/sendf.h b/Utilities/cmcurl/lib/sendf.h
index 5ef2b91..9ee00bb 100644
--- a/Utilities/cmcurl/lib/sendf.h
+++ b/Utilities/cmcurl/lib/sendf.h
@@ -28,18 +28,67 @@
#include "curl_trc.h"
-
-#define CLIENTWRITE_BODY (1<<0)
-#define CLIENTWRITE_HEADER (1<<1)
-#define CLIENTWRITE_STATUS (1<<2) /* the first "header" is the status line */
-#define CLIENTWRITE_CONNECT (1<<3) /* a CONNECT response */
-#define CLIENTWRITE_1XX (1<<4) /* a 1xx response */
-#define CLIENTWRITE_TRAILER (1<<5) /* a trailer header */
-#define CLIENTWRITE_BOTH (CLIENTWRITE_BODY|CLIENTWRITE_HEADER)
+/**
+ * Type of data that is being written to the client (application)
+ * - data written can be either BODY or META data
+ * - META data is either INFO or HEADER
+ * - INFO is meta information, e.g. not BODY, that cannot be interpreted
+ * as headers of a response. Example FTP/IMAP pingpong answers.
+ * - HEADER can have additional bits set (more than one)
+ * - STATUS special "header", e.g. response status line in HTTP
+ * - CONNECT header was received during proxying the connection
+ * - 1XX header is part of an intermediate response, e.g. HTTP 1xx code
+ * - TRAILER header is trailing response data, e.g. HTTP trailers
+ * BODY, INFO and HEADER should not be mixed, as this would lead to
+ * confusion on how to interpret/format/convert the data.
+ */
+#define CLIENTWRITE_BODY (1<<0) /* non-meta information, BODY */
+#define CLIENTWRITE_INFO (1<<1) /* meta information, not a HEADER */
+#define CLIENTWRITE_HEADER (1<<2) /* meta information, HEADER */
+#define CLIENTWRITE_STATUS (1<<3) /* a special status HEADER */
+#define CLIENTWRITE_CONNECT (1<<4) /* a CONNECT related HEADER */
+#define CLIENTWRITE_1XX (1<<5) /* a 1xx response related HEADER */
+#define CLIENTWRITE_TRAILER (1<<6) /* a trailer HEADER */
CURLcode Curl_client_write(struct Curl_easy *data, int type, char *ptr,
size_t len) WARN_UNUSED_RESULT;
+CURLcode Curl_client_unpause(struct Curl_easy *data);
+void Curl_client_cleanup(struct Curl_easy *data);
+
+struct contenc_writer {
+ const struct content_encoding *handler; /* Encoding handler. */
+ struct contenc_writer *downstream; /* Downstream writer. */
+ unsigned int order; /* Ordering within writer stack. */
+};
+
+/* Content encoding writer. */
+struct content_encoding {
+ const char *name; /* Encoding name. */
+ const char *alias; /* Encoding name alias. */
+ CURLcode (*init_writer)(struct Curl_easy *data,
+ struct contenc_writer *writer);
+ CURLcode (*unencode_write)(struct Curl_easy *data,
+ struct contenc_writer *writer,
+ const char *buf, size_t nbytes);
+ void (*close_writer)(struct Curl_easy *data,
+ struct contenc_writer *writer);
+ size_t writersize;
+};
+
+
+CURLcode Curl_client_create_writer(struct contenc_writer **pwriter,
+ struct Curl_easy *data,
+ const struct content_encoding *ce_handler,
+ int order);
+
+void Curl_client_free_writer(struct Curl_easy *data,
+ struct contenc_writer *writer);
+
+CURLcode Curl_client_add_writer(struct Curl_easy *data,
+ struct contenc_writer *writer);
+
+
/* internal read-function, does plain socket, SSL and krb4 */
CURLcode Curl_read(struct Curl_easy *data, curl_socket_t sockfd,
char *buf, size_t buffersize,
diff --git a/Utilities/cmcurl/lib/setopt.c b/Utilities/cmcurl/lib/setopt.c
index 2cef1b3..0d399ad 100644
--- a/Utilities/cmcurl/lib/setopt.c
+++ b/Utilities/cmcurl/lib/setopt.c
@@ -2076,7 +2076,7 @@ CURLcode Curl_vsetopt(struct Curl_easy *data, CURLoption option, va_list param)
else
#endif
result = CURLE_NOT_BUILT_IN;
- break;
+ break;
case CURLOPT_PINNEDPUBLICKEY:
/*
* Set pinned public key for SSL connection.
diff --git a/Utilities/cmcurl/lib/sigpipe.h b/Utilities/cmcurl/lib/sigpipe.h
index 48761ad..9b29403 100644
--- a/Utilities/cmcurl/lib/sigpipe.h
+++ b/Utilities/cmcurl/lib/sigpipe.h
@@ -25,7 +25,7 @@
***************************************************************************/
#include "curl_setup.h"
-#if defined(HAVE_SIGNAL_H) && defined(HAVE_SIGACTION) && \
+#if defined(HAVE_SIGACTION) && \
(defined(USE_OPENSSL) || defined(USE_MBEDTLS) || defined(USE_WOLFSSL))
#include <signal.h>
diff --git a/Utilities/cmcurl/lib/smb.c b/Utilities/cmcurl/lib/smb.c
index afcc99d..32c5137 100644
--- a/Utilities/cmcurl/lib/smb.c
+++ b/Utilities/cmcurl/lib/smb.c
@@ -1049,7 +1049,12 @@ static CURLcode smb_request_state(struct Curl_easy *data, bool *done)
}
data->req.bytecount += len;
data->req.offset += len;
- Curl_pgrsSetDownloadCounter(data, data->req.bytecount);
+ result = Curl_pgrsSetDownloadCounter(data, data->req.bytecount);
+ if(result) {
+ req->result = result;
+ next_state = SMB_CLOSE;
+ break;
+ }
next_state = (len < MAX_PAYLOAD_SIZE) ? SMB_CLOSE : SMB_DOWNLOAD;
break;
diff --git a/Utilities/cmcurl/lib/socks.c b/Utilities/cmcurl/lib/socks.c
index c492d66..a7b5ab0 100644
--- a/Utilities/cmcurl/lib/socks.c
+++ b/Utilities/cmcurl/lib/socks.c
@@ -587,9 +587,9 @@ static CURLproxycode do_SOCKS5(struct Curl_cfilter *cf,
/* RFC1928 chapter 5 specifies max 255 chars for domain name in packet */
if(!socks5_resolve_local && hostname_len > 255) {
- infof(data, "SOCKS5: server resolving disabled for hostnames of "
- "length > 255 [actual len=%zu]", hostname_len);
- socks5_resolve_local = TRUE;
+ failf(data, "SOCKS5: the destination hostname is too long to be "
+ "resolved remotely by the proxy.");
+ return CURLPX_LONG_HOSTNAME;
}
if(auth & ~(CURLAUTH_BASIC | CURLAUTH_GSSAPI))
@@ -903,7 +903,7 @@ CONNECT_RESOLVE_REMOTE:
}
else {
socksreq[len++] = 3;
- socksreq[len++] = (char) hostname_len; /* one byte address length */
+ socksreq[len++] = (unsigned char) hostname_len; /* one byte length */
memcpy(&socksreq[len], sx->hostname, hostname_len); /* w/o NULL */
len += hostname_len;
}
diff --git a/Utilities/cmcurl/lib/telnet.c b/Utilities/cmcurl/lib/telnet.c
index 850f88c..836e255 100644
--- a/Utilities/cmcurl/lib/telnet.c
+++ b/Utilities/cmcurl/lib/telnet.c
@@ -1570,8 +1570,9 @@ static CURLcode telnet_do(struct Curl_easy *data, bool *done)
}
total_dl += nread;
- Curl_pgrsSetDownloadCounter(data, total_dl);
- result = telrcv(data, (unsigned char *)buf, nread);
+ result = Curl_pgrsSetDownloadCounter(data, total_dl);
+ if(!result)
+ result = telrcv(data, (unsigned char *)buf, nread);
if(result) {
keepon = FALSE;
break;
diff --git a/Utilities/cmcurl/lib/tftp.c b/Utilities/cmcurl/lib/tftp.c
index 8ed1b88..e78140d 100644
--- a/Utilities/cmcurl/lib/tftp.c
+++ b/Utilities/cmcurl/lib/tftp.c
@@ -1141,12 +1141,15 @@ static CURLcode tftp_receive_packet(struct Curl_easy *data)
result = Curl_client_write(data, CLIENTWRITE_BODY,
(char *)state->rpacket.data + 4,
state->rbytes-4);
+ if(!result) {
+ k->bytecount += state->rbytes-4;
+ result = Curl_pgrsSetDownloadCounter(data,
+ (curl_off_t) k->bytecount);
+ }
if(result) {
tftp_state_machine(state, TFTP_EVENT_ERROR);
return result;
}
- k->bytecount += state->rbytes-4;
- Curl_pgrsSetDownloadCounter(data, (curl_off_t) k->bytecount);
}
break;
case TFTP_EVENT_ERROR:
diff --git a/Utilities/cmcurl/lib/timeval.c b/Utilities/cmcurl/lib/timeval.c
index 2de79be..026d9d1 100644
--- a/Utilities/cmcurl/lib/timeval.c
+++ b/Utilities/cmcurl/lib/timeval.c
@@ -210,6 +210,20 @@ timediff_t Curl_timediff(struct curltime newer, struct curltime older)
}
/*
+ * Returns: time difference in number of milliseconds, rounded up.
+ * For too large diffs it returns max value.
+ */
+timediff_t Curl_timediff_ceil(struct curltime newer, struct curltime older)
+{
+ timediff_t diff = (timediff_t)newer.tv_sec-older.tv_sec;
+ if(diff >= (TIMEDIFF_T_MAX/1000))
+ return TIMEDIFF_T_MAX;
+ else if(diff <= (TIMEDIFF_T_MIN/1000))
+ return TIMEDIFF_T_MIN;
+ return diff * 1000 + (newer.tv_usec - older.tv_usec + 999)/1000;
+}
+
+/*
* Returns: time difference in number of microseconds. For too large diffs it
* returns max value.
*/
diff --git a/Utilities/cmcurl/lib/timeval.h b/Utilities/cmcurl/lib/timeval.h
index 92e484a..33dfb5b 100644
--- a/Utilities/cmcurl/lib/timeval.h
+++ b/Utilities/cmcurl/lib/timeval.h
@@ -36,16 +36,24 @@ struct curltime {
struct curltime Curl_now(void);
/*
- * Make sure that the first argument (t1) is the more recent time and t2 is
- * the older time, as otherwise you get a weird negative time-diff back...
+ * Make sure that the first argument (newer) is the more recent time and older
+ * is the older time, as otherwise you get a weird negative time-diff back...
*
* Returns: the time difference in number of milliseconds.
*/
-timediff_t Curl_timediff(struct curltime t1, struct curltime t2);
+timediff_t Curl_timediff(struct curltime newer, struct curltime older);
/*
- * Make sure that the first argument (t1) is the more recent time and t2 is
- * the older time, as otherwise you get a weird negative time-diff back...
+ * Make sure that the first argument (newer) is the more recent time and older
+ * is the older time, as otherwise you get a weird negative time-diff back...
+ *
+ * Returns: the time difference in number of milliseconds, rounded up.
+ */
+timediff_t Curl_timediff_ceil(struct curltime newer, struct curltime older);
+
+/*
+ * Make sure that the first argument (newer) is the more recent time and older
+ * is the older time, as otherwise you get a weird negative time-diff back...
*
* Returns: the time difference in number of microseconds.
*/
diff --git a/Utilities/cmcurl/lib/transfer.c b/Utilities/cmcurl/lib/transfer.c
index d0602b8..6886764 100644
--- a/Utilities/cmcurl/lib/transfer.c
+++ b/Utilities/cmcurl/lib/transfer.c
@@ -40,9 +40,7 @@
#ifdef HAVE_SYS_IOCTL_H
#include <sys/ioctl.h>
#endif
-#ifdef HAVE_SIGNAL_H
#include <signal.h>
-#endif
#ifdef HAVE_SYS_PARAM_H
#include <sys/param.h>
@@ -671,7 +669,9 @@ static CURLcode readwrite_data(struct Curl_easy *data,
k->bytecount += nread;
max_recv -= nread;
- Curl_pgrsSetDownloadCounter(data, k->bytecount);
+ result = Curl_pgrsSetDownloadCounter(data, k->bytecount);
+ if(result)
+ goto out;
if(!k->chunk && (nread || k->badheader || is_empty_data)) {
/* If this is chunky transfer, it was already written */
@@ -700,19 +700,15 @@ static CURLcode readwrite_data(struct Curl_easy *data,
in http_chunks.c.
Make sure that ALL_CONTENT_ENCODINGS contains all the
encodings handled here. */
- if(data->set.http_ce_skip || !k->writer_stack) {
- if(!k->ignorebody && nread) {
+ if(!k->ignorebody && nread) {
#ifndef CURL_DISABLE_POP3
- if(conn->handler->protocol & PROTO_FAMILY_POP3)
- result = Curl_pop3_write(data, k->str, nread);
- else
+ if(conn->handler->protocol & PROTO_FAMILY_POP3)
+ result = Curl_pop3_write(data, k->str, nread);
+ else
#endif /* CURL_DISABLE_POP3 */
- result = Curl_client_write(data, CLIENTWRITE_BODY, k->str,
- nread);
- }
+ result = Curl_client_write(data, CLIENTWRITE_BODY, k->str,
+ nread);
}
- else if(!k->ignorebody && nread)
- result = Curl_unencode_write(data, k->writer_stack, k->str, nread);
}
k->badheader = HEADER_NORMAL; /* taken care of now */
@@ -1050,6 +1046,19 @@ static CURLcode readwrite_upload(struct Curl_easy *data,
return CURLE_OK;
}
+static int select_bits_paused(struct Curl_easy *data, int select_bits)
+{
+ /* See issue #11982: we really need to be careful not to progress
+ * a transfer direction when that direction is paused. Not all parts
+ * of our state machine are handling PAUSED transfers correctly. So, we
+ * do not want to go there.
+ * NOTE: we are only interested in PAUSE, not HOLD. */
+ return (((select_bits & CURL_CSELECT_IN) &&
+ (data->req.keepon & KEEP_RECV_PAUSE)) ||
+ ((select_bits & CURL_CSELECT_OUT) &&
+ (data->req.keepon & KEEP_SEND_PAUSE)));
+}
+
/*
* Curl_readwrite() is the low-level function to be called when data is to
* be read and written to/from the connection.
@@ -1068,12 +1077,20 @@ CURLcode Curl_readwrite(struct connectdata *conn,
int didwhat = 0;
int select_bits;
-
if(data->state.dselect_bits) {
+ if(select_bits_paused(data, data->state.dselect_bits)) {
+ /* leave the bits unchanged, so they'll tell us what to do when
+ * this transfer gets unpaused. */
+ DEBUGF(infof(data, "readwrite, dselect_bits, early return on PAUSED"));
+ result = CURLE_OK;
+ goto out;
+ }
select_bits = data->state.dselect_bits;
data->state.dselect_bits = 0;
}
else if(conn->cselect_bits) {
+ /* CAVEAT: adding `select_bits_paused()` check here makes test640 hang
+ * (among others). Which hints at strange state handling in FTP land... */
select_bits = conn->cselect_bits;
conn->cselect_bits = 0;
}
diff --git a/Utilities/cmcurl/lib/url.c b/Utilities/cmcurl/lib/url.c
index 4f5673e..61dad44 100644
--- a/Utilities/cmcurl/lib/url.c
+++ b/Utilities/cmcurl/lib/url.c
@@ -888,8 +888,8 @@ static bool conn_maxage(struct Curl_easy *data,
idletime /= 1000; /* integer seconds is fine */
if(idletime > data->set.maxage_conn) {
- infof(data, "Too old connection (%ld seconds idle), disconnect it",
- idletime);
+ infof(data, "Too old connection (%" CURL_FORMAT_TIMEDIFF_T
+ " seconds idle), disconnect it", idletime);
return TRUE;
}
@@ -898,8 +898,8 @@ static bool conn_maxage(struct Curl_easy *data,
if(data->set.maxlifetime_conn && lifetime > data->set.maxlifetime_conn) {
infof(data,
- "Too old connection (%ld seconds since creation), disconnect it",
- lifetime);
+ "Too old connection (%" CURL_FORMAT_TIMEDIFF_T
+ " seconds since creation), disconnect it", lifetime);
return TRUE;
}
@@ -1169,7 +1169,7 @@ ConnectionExists(struct Curl_easy *data,
foundPendingCandidate = TRUE;
/* Don't pick a connection that hasn't connected yet */
infof(data, "Connection #%" CURL_FORMAT_CURL_OFF_T
- "isn't open enough, can't reuse", check->connection_id);
+ " isn't open enough, can't reuse", check->connection_id);
continue;
}
@@ -2033,13 +2033,13 @@ void Curl_free_request_state(struct Curl_easy *data)
{
Curl_safefree(data->req.p.http);
Curl_safefree(data->req.newurl);
-
#ifndef CURL_DISABLE_DOH
if(data->req.doh) {
Curl_close(&data->req.doh->probe[0].easy);
Curl_close(&data->req.doh->probe[1].easy);
}
#endif
+ Curl_client_cleanup(data);
}
@@ -2076,7 +2076,6 @@ static char *detect_proxy(struct Curl_easy *data,
char proxy_env[128];
const char *protop = conn->handler->scheme;
char *envp = proxy_env;
- char *prox;
#ifdef CURL_DISABLE_VERBOSE_STRINGS
(void)data;
#endif
@@ -2089,7 +2088,7 @@ static char *detect_proxy(struct Curl_easy *data,
strcpy(envp, "_proxy");
/* read the protocol proxy: */
- prox = curl_getenv(proxy_env);
+ proxy = curl_getenv(proxy_env);
/*
* We don't try the uppercase version of HTTP_PROXY because of
@@ -2103,23 +2102,35 @@ static char *detect_proxy(struct Curl_easy *data,
* This can cause 'internal' http/ftp requests to be
* arbitrarily redirected by any external attacker.
*/
- if(!prox && !strcasecompare("http_proxy", proxy_env)) {
+ if(!proxy && !strcasecompare("http_proxy", proxy_env)) {
/* There was no lowercase variable, try the uppercase version: */
Curl_strntoupper(proxy_env, proxy_env, sizeof(proxy_env));
- prox = curl_getenv(proxy_env);
+ proxy = curl_getenv(proxy_env);
}
envp = proxy_env;
- if(prox) {
- proxy = prox; /* use this */
- }
- else {
- envp = (char *)"all_proxy";
- proxy = curl_getenv(envp); /* default proxy to use */
+ if(!proxy) {
+#ifdef USE_WEBSOCKETS
+ /* websocket proxy fallbacks */
+ if(strcasecompare("ws_proxy", proxy_env)) {
+ proxy = curl_getenv("http_proxy");
+ }
+ else if(strcasecompare("wss_proxy", proxy_env)) {
+ proxy = curl_getenv("https_proxy");
+ if(!proxy)
+ proxy = curl_getenv("HTTPS_PROXY");
+ }
if(!proxy) {
- envp = (char *)"ALL_PROXY";
- proxy = curl_getenv(envp);
+#endif
+ envp = (char *)"all_proxy";
+ proxy = curl_getenv(envp); /* default proxy to use */
+ if(!proxy) {
+ envp = (char *)"ALL_PROXY";
+ proxy = curl_getenv(envp);
+ }
+#ifdef USE_WEBSOCKETS
}
+#endif
}
if(proxy)
infof(data, "Uses proxy env variable %s == '%s'", envp, proxy);
@@ -2719,7 +2730,9 @@ static CURLcode override_login(struct Curl_easy *data,
data->set.str[STRING_NETRC_FILE]);
if(ret > 0) {
infof(data, "Couldn't find host %s in the %s file; using defaults",
- conn->host.name, data->set.str[STRING_NETRC_FILE]);
+ conn->host.name,
+ (data->set.str[STRING_NETRC_FILE] ?
+ data->set.str[STRING_NETRC_FILE] : ".netrc"));
}
else if(ret < 0) {
failf(data, ".netrc parser error");
@@ -3214,8 +3227,8 @@ static CURLcode resolve_host(struct Curl_easy *data,
if(rc == CURLRESOLV_PENDING)
*async = TRUE;
else if(rc == CURLRESOLV_TIMEDOUT) {
- failf(data, "Failed to resolve host '%s' with timeout after %ld ms",
- connhost->dispname,
+ failf(data, "Failed to resolve host '%s' with timeout after %"
+ CURL_FORMAT_TIMEDIFF_T " ms", connhost->dispname,
Curl_timediff(Curl_now(), data->progress.t_startsingle));
return CURLE_OPERATION_TIMEDOUT;
}
diff --git a/Utilities/cmcurl/lib/urlapi.c b/Utilities/cmcurl/lib/urlapi.c
index 80299e7..4efab61 100644
--- a/Utilities/cmcurl/lib/urlapi.c
+++ b/Utilities/cmcurl/lib/urlapi.c
@@ -100,7 +100,7 @@ static void free_urlhandle(struct Curl_URL *u)
/*
* Find the separator at the end of the host name, or the '?' in cases like
- * http://www.url.com?id=2380
+ * http://www.example.com?id=2380
*/
static const char *find_host_sep(const char *url)
{
@@ -338,7 +338,7 @@ static char *concat_url(char *base, const char *relurl)
pathsep = strchr(protsep, '/');
if(pathsep) {
/* When people use badly formatted URLs, such as
- "http://www.url.com?dir=/home/daniel" we must not use the first
+ "http://www.example.com?dir=/home/daniel" we must not use the first
slash, if there's a ?-letter before it! */
char *sep = strchr(protsep, '?');
if(sep && (sep < pathsep))
@@ -347,9 +347,9 @@ static char *concat_url(char *base, const char *relurl)
}
else {
/* There was no slash. Now, since we might be operating on a badly
- formatted URL, such as "http://www.url.com?id=2380" which doesn't
- use a slash separator as it is supposed to, we need to check for a
- ?-letter as well! */
+ formatted URL, such as "http://www.example.com?id=2380" which
+ doesn't use a slash separator as it is supposed to, we need to check
+ for a ?-letter as well! */
pathsep = strchr(protsep, '?');
if(pathsep)
*pathsep = 0;
@@ -1865,7 +1865,7 @@ CURLUcode curl_url_set(CURLU *u, CURLUPart what,
if(result)
return CURLUE_OUT_OF_MEMORY;
}
- else if(Curl_isunreserved(*i) ||
+ else if(ISUNRESERVED(*i) ||
((*i == '/') && urlskipslash) ||
((*i == '=') && equalsencode)) {
if((*i == '=') && equalsencode)
diff --git a/Utilities/cmcurl/lib/urldata.h b/Utilities/cmcurl/lib/urldata.h
index 4bfb3b4..dff26e6 100644
--- a/Utilities/cmcurl/lib/urldata.h
+++ b/Utilities/cmcurl/lib/urldata.h
@@ -640,7 +640,9 @@ struct SingleRequest {
curl_off_t pendingheader; /* this many bytes left to send is actually
header and not body */
struct curltime start; /* transfer started at this time */
- unsigned int headerbytecount; /* only count received headers */
+ unsigned int headerbytecount; /* received server headers (not CONNECT
+ headers) */
+ unsigned int allheadercount; /* all received headers (server + CONNECT) */
unsigned int deductheadercount; /* this amount of bytes doesn't count when
we check if anything has been transferred
at the end of a connection. We use this
@@ -1260,6 +1262,7 @@ struct tempbuf {
struct dynbuf b;
int type; /* type of the 'tempwrite' buffer as a bitmask that is used with
Curl_client_write() */
+ BIT(paused_body); /* if PAUSE happened before/during BODY write */
};
/* Timers */
@@ -1947,7 +1950,7 @@ struct Curl_easy {
other using the same cache. For easier tracking
in log output.
This may wrap around after LONG_MAX to 0 again, so it
- has no uniqueness guarantuee for very large processings. */
+ has no uniqueness guarantee for very large processings. */
curl_off_t id;
/* first, two fields for the linked list of these */
@@ -2010,6 +2013,10 @@ struct Curl_easy {
#ifdef USE_HYPER
struct hyptransfer hyp;
#endif
+
+ /* internal: true if this easy handle was created for internal use and the
+ user does not have ownership of the handle. */
+ bool internal;
};
#define LIBCURL_NAME "libcurl"
diff --git a/Utilities/cmcurl/lib/vauth/cleartext.c b/Utilities/cmcurl/lib/vauth/cleartext.c
index c651fc5..972a874 100644
--- a/Utilities/cmcurl/lib/vauth/cleartext.c
+++ b/Utilities/cmcurl/lib/vauth/cleartext.c
@@ -35,7 +35,6 @@
#include "urldata.h"
#include "vauth/vauth.h"
-#include "curl_md5.h"
#include "warnless.h"
#include "strtok.h"
#include "sendf.h"
diff --git a/Utilities/cmcurl/lib/vquic/curl_ngtcp2.c b/Utilities/cmcurl/lib/vquic/curl_ngtcp2.c
index 03e911d..7d681e5 100644
--- a/Utilities/cmcurl/lib/vquic/curl_ngtcp2.c
+++ b/Utilities/cmcurl/lib/vquic/curl_ngtcp2.c
@@ -30,7 +30,7 @@
#ifdef USE_OPENSSL
#include <openssl/err.h>
-#ifdef OPENSSL_IS_BORINGSSL
+#if defined(OPENSSL_IS_BORINGSSL) || defined(OPENSSL_IS_AWSLC)
#include <ngtcp2/ngtcp2_crypto_boringssl.h>
#else
#include <ngtcp2/ngtcp2_crypto_quictls.h>
@@ -407,7 +407,7 @@ static CURLcode quic_ssl_ctx(SSL_CTX **pssl_ctx,
goto out;
}
-#ifdef OPENSSL_IS_BORINGSSL
+#if defined(OPENSSL_IS_BORINGSSL) || defined(OPENSSL_IS_AWSLC)
if(ngtcp2_crypto_boringssl_configure_client_context(ssl_ctx) != 0) {
failf(data, "ngtcp2_crypto_boringssl_configure_client_context failed");
goto out;
@@ -421,22 +421,24 @@ static CURLcode quic_ssl_ctx(SSL_CTX **pssl_ctx,
SSL_CTX_set_default_verify_paths(ssl_ctx);
-#ifdef OPENSSL_IS_BORINGSSL
- if(SSL_CTX_set1_curves_list(ssl_ctx, QUIC_GROUPS) != 1) {
- failf(data, "SSL_CTX_set1_curves_list failed");
- goto out;
- }
-#else
- if(SSL_CTX_set_ciphersuites(ssl_ctx, QUIC_CIPHERS) != 1) {
- char error_buffer[256];
- ERR_error_string_n(ERR_get_error(), error_buffer, sizeof(error_buffer));
- failf(data, "SSL_CTX_set_ciphersuites: %s", error_buffer);
- goto out;
+ {
+ const char *curves = conn->ssl_config.curves ?
+ conn->ssl_config.curves : QUIC_GROUPS;
+ if(!SSL_CTX_set1_curves_list(ssl_ctx, curves)) {
+ failf(data, "failed setting curves list for QUIC: '%s'", curves);
+ return CURLE_SSL_CIPHER;
+ }
}
- if(SSL_CTX_set1_groups_list(ssl_ctx, QUIC_GROUPS) != 1) {
- failf(data, "SSL_CTX_set1_groups_list failed");
- goto out;
+#ifndef OPENSSL_IS_BORINGSSL
+ {
+ const char *ciphers13 = conn->ssl_config.cipher_list13 ?
+ conn->ssl_config.cipher_list13 : QUIC_CIPHERS;
+ if(SSL_CTX_set_ciphersuites(ssl_ctx, ciphers13) != 1) {
+ failf(data, "failed setting QUIC cipher suite: %s", ciphers13);
+ return CURLE_SSL_CIPHER;
+ }
+ infof(data, "QUIC cipher selection: %s", ciphers13);
}
#endif
@@ -616,15 +618,19 @@ static CURLcode quic_ssl_ctx(WOLFSSL_CTX **pssl_ctx,
wolfSSL_CTX_set_default_verify_paths(ssl_ctx);
- if(wolfSSL_CTX_set_cipher_list(ssl_ctx, QUIC_CIPHERS) != 1) {
+ if(wolfSSL_CTX_set_cipher_list(ssl_ctx, conn->ssl_config.cipher_list13 ?
+ conn->ssl_config.cipher_list13 :
+ QUIC_CIPHERS) != 1) {
char error_buffer[256];
ERR_error_string_n(ERR_get_error(), error_buffer, sizeof(error_buffer));
- failf(data, "wolfSSL_CTX_set_cipher_list: %s", error_buffer);
+ failf(data, "wolfSSL failed to set ciphers: %s", error_buffer);
goto out;
}
- if(wolfSSL_CTX_set1_groups_list(ssl_ctx, (char *)QUIC_GROUPS) != 1) {
- failf(data, "SSL_CTX_set1_groups_list failed");
+ if(wolfSSL_CTX_set1_groups_list(ssl_ctx, conn->ssl_config.curves ?
+ conn->ssl_config.curves :
+ (char *)QUIC_GROUPS) != 1) {
+ failf(data, "wolfSSL failed to set curves");
goto out;
}
@@ -644,10 +650,13 @@ static CURLcode quic_ssl_ctx(WOLFSSL_CTX **pssl_ctx,
const char * const ssl_capath = conn->ssl_config.CApath;
wolfSSL_CTX_set_verify(ssl_ctx, SSL_VERIFY_PEER, NULL);
- if(conn->ssl_config.CAfile || conn->ssl_config.CApath) {
+ if(ssl_cafile || ssl_capath) {
/* tell wolfSSL where to find CA certificates that are used to verify
the server's certificate. */
- if(!wolfSSL_CTX_load_verify_locations(ssl_ctx, ssl_cafile, ssl_capath)) {
+ int rc =
+ wolfSSL_CTX_load_verify_locations_ex(ssl_ctx, ssl_cafile, ssl_capath,
+ WOLFSSL_LOAD_FLAG_IGNORE_ERR);
+ if(SSL_SUCCESS != rc) {
/* Fail if we insist on successfully verifying the server. */
failf(data, "error setting certificate verify locations:"
" CAfile: %s CApath: %s",
diff --git a/Utilities/cmcurl/lib/vquic/curl_quiche.c b/Utilities/cmcurl/lib/vquic/curl_quiche.c
index 3598de1..3f5d327 100644
--- a/Utilities/cmcurl/lib/vquic/curl_quiche.c
+++ b/Utilities/cmcurl/lib/vquic/curl_quiche.c
@@ -149,8 +149,8 @@ static CURLcode quic_x509_store_setup(struct Curl_cfilter *cf,
SSL_CTX_set_verify(ctx->sslctx, SSL_VERIFY_PEER, NULL);
/* tell OpenSSL where to find CA certificates that are used to verify
the server's certificate. */
- if(!SSL_CTX_load_verify_locations(
- ctx->sslctx, ssl_cafile, ssl_capath)) {
+ if(!SSL_CTX_load_verify_locations(ctx->sslctx, ssl_cafile,
+ ssl_capath)) {
/* Fail if we insist on successfully verifying the server. */
failf(data, "error setting certificate verify locations:"
" CAfile: %s CApath: %s",
@@ -165,7 +165,7 @@ static CURLcode quic_x509_store_setup(struct Curl_cfilter *cf,
else {
/* verifying the peer without any CA certificates won't work so
use openssl's built-in default as fallback */
- SSL_CTX_set_default_verify_paths(ssl_ctx);
+ SSL_CTX_set_default_verify_paths(ctx->sslctx);
}
#endif
}
@@ -178,6 +178,8 @@ static CURLcode quic_ssl_setup(struct Curl_cfilter *cf, struct Curl_easy *data)
{
struct cf_quiche_ctx *ctx = cf->ctx;
unsigned char checkip[16];
+ struct connectdata *conn = data->conn;
+ const char *curves = conn->ssl_config.curves;
DEBUGASSERT(!ctx->sslctx);
ctx->sslctx = SSL_CTX_new(TLS_method());
@@ -196,6 +198,11 @@ static CURLcode quic_ssl_setup(struct Curl_cfilter *cf, struct Curl_easy *data)
SSL_CTX_set_keylog_callback(ctx->sslctx, keylog_callback);
}
+ if(curves && !SSL_CTX_set1_curves_list(ctx->sslctx, curves)) {
+ failf(data, "failed setting curves list for QUIC: '%s'", curves);
+ return CURLE_SSL_CIPHER;
+ }
+
ctx->ssl = SSL_new(ctx->sslctx);
if(!ctx->ssl)
return CURLE_QUIC_CONNECT_ERROR;
diff --git a/Utilities/cmcurl/lib/vssh/libssh.c b/Utilities/cmcurl/lib/vssh/libssh.c
index dea0084..b0f49d6 100644
--- a/Utilities/cmcurl/lib/vssh/libssh.c
+++ b/Utilities/cmcurl/lib/vssh/libssh.c
@@ -2567,6 +2567,12 @@ static ssize_t sftp_send(struct Curl_easy *data, int sockindex,
struct connectdata *conn = data->conn;
(void)sockindex;
+ /* limit the writes to the maximum specified in Section 3 of
+ * https://datatracker.ietf.org/doc/html/draft-ietf-secsh-filexfer-02
+ */
+ if(len > 32768)
+ len = 32768;
+
nwrite = sftp_write(conn->proto.sshc.sftp_file, mem, len);
myssh_block2waitfor(conn, FALSE);
@@ -2654,7 +2660,7 @@ static void sftp_quote(struct Curl_easy *data)
/* if a command starts with an asterisk, which a legal SFTP command never
can, the command will be allowed to fail without it causing any
aborts or cancels etc. It will cause libcurl to act as if the command
- is successful, whatever the server reponds. */
+ is successful, whatever the server responds. */
if(cmd[0] == '*') {
cmd++;
@@ -2828,7 +2834,7 @@ static void sftp_quote_stat(struct Curl_easy *data)
/* if a command starts with an asterisk, which a legal SFTP command never
can, the command will be allowed to fail without it causing any
aborts or cancels etc. It will cause libcurl to act as if the command
- is successful, whatever the server reponds. */
+ is successful, whatever the server responds. */
if(cmd[0] == '*') {
cmd++;
diff --git a/Utilities/cmcurl/lib/vssh/libssh2.c b/Utilities/cmcurl/lib/vssh/libssh2.c
index 37040b4..f539b39 100644
--- a/Utilities/cmcurl/lib/vssh/libssh2.c
+++ b/Utilities/cmcurl/lib/vssh/libssh2.c
@@ -1178,8 +1178,16 @@ static CURLcode ssh_statemach_act(struct Curl_easy *data, bool *block)
}
else {
char *err_msg = NULL;
- (void)libssh2_session_last_error(sshc->ssh_session,
- &err_msg, NULL, 0);
+ char unknown[] = "Reason unknown (-1)";
+ if(rc == -1) {
+ /* No error message has been set and the last set error message, if
+ any, is from a previous error so ignore it. #11837 */
+ err_msg = unknown;
+ }
+ else {
+ (void)libssh2_session_last_error(sshc->ssh_session,
+ &err_msg, NULL, 0);
+ }
infof(data, "SSH public key authentication failed: %s", err_msg);
state(data, SSH_AUTH_PASS_INIT);
rc = 0; /* clear rc and continue */
@@ -1495,7 +1503,7 @@ static CURLcode ssh_statemach_act(struct Curl_easy *data, bool *block)
/* if a command starts with an asterisk, which a legal SFTP command never
can, the command will be allowed to fail without it causing any
aborts or cancels etc. It will cause libcurl to act as if the command
- is successful, whatever the server reponds. */
+ is successful, whatever the server responds. */
if(cmd[0] == '*') {
cmd++;
@@ -1691,7 +1699,7 @@ static CURLcode ssh_statemach_act(struct Curl_easy *data, bool *block)
/* if a command starts with an asterisk, which a legal SFTP command never
can, the command will be allowed to fail without it causing any
aborts or cancels etc. It will cause libcurl to act as if the command
- is successful, whatever the server reponds. */
+ is successful, whatever the server responds. */
if(cmd[0] == '*') {
cmd++;
diff --git a/Utilities/cmcurl/lib/vssh/wolfssh.c b/Utilities/cmcurl/lib/vssh/wolfssh.c
index 306d299..39cee50 100644
--- a/Utilities/cmcurl/lib/vssh/wolfssh.c
+++ b/Utilities/cmcurl/lib/vssh/wolfssh.c
@@ -1168,6 +1168,7 @@ CURLcode Curl_ssh_init(void)
}
void Curl_ssh_cleanup(void)
{
+ (void)wolfSSH_Cleanup();
}
#endif /* USE_WOLFSSH */
diff --git a/Utilities/cmcurl/lib/vtls/gtls.c b/Utilities/cmcurl/lib/vtls/gtls.c
index e483469..c538a96 100644
--- a/Utilities/cmcurl/lib/vtls/gtls.c
+++ b/Utilities/cmcurl/lib/vtls/gtls.c
@@ -1473,7 +1473,6 @@ static int gtls_shutdown(struct Curl_cfilter *cf,
struct Curl_easy *data)
{
struct ssl_connect_data *connssl = cf->ctx;
- struct ssl_config_data *ssl_config = Curl_ssl_cf_get_config(cf, data);
struct gtls_ssl_backend_data *backend =
(struct gtls_ssl_backend_data *)connssl->backend;
int retval = 0;
@@ -1536,8 +1535,11 @@ static int gtls_shutdown(struct Curl_cfilter *cf,
gnutls_certificate_free_credentials(backend->gtls.cred);
#ifdef USE_GNUTLS_SRP
- if(ssl_config->primary.username)
- gnutls_srp_free_client_credentials(backend->gtls.srp_client_cred);
+ {
+ struct ssl_config_data *ssl_config = Curl_ssl_cf_get_config(cf, data);
+ if(ssl_config->primary.username)
+ gnutls_srp_free_client_credentials(backend->gtls.srp_client_cred);
+ }
#endif
backend->gtls.cred = NULL;
diff --git a/Utilities/cmcurl/lib/vtls/mbedtls.c b/Utilities/cmcurl/lib/vtls/mbedtls.c
index f45636e..2f994d7 100644
--- a/Utilities/cmcurl/lib/vtls/mbedtls.c
+++ b/Utilities/cmcurl/lib/vtls/mbedtls.c
@@ -156,7 +156,8 @@ static void mbed_debug(void *context, int level, const char *f_name,
#else
#endif
-static int bio_cf_write(void *bio, const unsigned char *buf, size_t blen)
+static int mbedtls_bio_cf_write(void *bio,
+ const unsigned char *buf, size_t blen)
{
struct Curl_cfilter *cf = bio;
struct Curl_easy *data = CF_DATA_CURRENT(cf);
@@ -165,7 +166,7 @@ static int bio_cf_write(void *bio, const unsigned char *buf, size_t blen)
DEBUGASSERT(data);
nwritten = Curl_conn_cf_send(cf->next, data, (char *)buf, blen, &result);
- CURL_TRC_CF(data, cf, "bio_cf_out_write(len=%zu) -> %zd, err=%d",
+ CURL_TRC_CF(data, cf, "mbedtls_bio_cf_out_write(len=%zu) -> %zd, err=%d",
blen, nwritten, result);
if(nwritten < 0 && CURLE_AGAIN == result) {
nwritten = MBEDTLS_ERR_SSL_WANT_WRITE;
@@ -173,7 +174,7 @@ static int bio_cf_write(void *bio, const unsigned char *buf, size_t blen)
return (int)nwritten;
}
-static int bio_cf_read(void *bio, unsigned char *buf, size_t blen)
+static int mbedtls_bio_cf_read(void *bio, unsigned char *buf, size_t blen)
{
struct Curl_cfilter *cf = bio;
struct Curl_easy *data = CF_DATA_CURRENT(cf);
@@ -186,7 +187,7 @@ static int bio_cf_read(void *bio, unsigned char *buf, size_t blen)
return 0;
nread = Curl_conn_cf_recv(cf->next, data, (char *)buf, blen, &result);
- CURL_TRC_CF(data, cf, "bio_cf_in_read(len=%zu) -> %zd, err=%d",
+ CURL_TRC_CF(data, cf, "mbedtls_bio_cf_in_read(len=%zu) -> %zd, err=%d",
blen, nread, result);
if(nread < 0 && CURLE_AGAIN == result) {
nread = MBEDTLS_ERR_SSL_WANT_READ;
@@ -591,7 +592,9 @@ mbed_connect_step1(struct Curl_cfilter *cf, struct Curl_easy *data)
mbedtls_ssl_conf_rng(&backend->config, mbedtls_ctr_drbg_random,
&backend->ctr_drbg);
- mbedtls_ssl_set_bio(&backend->ssl, cf, bio_cf_write, bio_cf_read,
+ mbedtls_ssl_set_bio(&backend->ssl, cf,
+ mbedtls_bio_cf_write,
+ mbedtls_bio_cf_read,
NULL /* rev_timeout() */);
mbedtls_ssl_conf_ciphersuites(&backend->config,
diff --git a/Utilities/cmcurl/lib/vtls/openssl.c b/Utilities/cmcurl/lib/vtls/openssl.c
index ee3a714..15d84ed 100644
--- a/Utilities/cmcurl/lib/vtls/openssl.c
+++ b/Utilities/cmcurl/lib/vtls/openssl.c
@@ -474,7 +474,9 @@ CURLcode Curl_ossl_certchain(struct Curl_easy *data, SSL *ssl)
X509_get0_signature(&psig, &sigalg, x);
if(sigalg) {
- i2a_ASN1_OBJECT(mem, sigalg->algorithm);
+ const ASN1_OBJECT *sigalgoid = NULL;
+ X509_ALGOR_get0(&sigalgoid, NULL, NULL, sigalg);
+ i2a_ASN1_OBJECT(mem, sigalgoid);
push_certinfo("Signature Algorithm", i);
}
@@ -669,7 +671,7 @@ CURLcode Curl_ossl_certchain(struct Curl_easy *data, SSL *ssl)
#define BIO_set_shutdown(x,v) ((x)->shutdown=(v))
#endif /* USE_PRE_1_1_API */
-static int bio_cf_create(BIO *bio)
+static int ossl_bio_cf_create(BIO *bio)
{
BIO_set_shutdown(bio, 1);
BIO_set_init(bio, 1);
@@ -680,14 +682,14 @@ static int bio_cf_create(BIO *bio)
return 1;
}
-static int bio_cf_destroy(BIO *bio)
+static int ossl_bio_cf_destroy(BIO *bio)
{
if(!bio)
return 0;
return 1;
}
-static long bio_cf_ctrl(BIO *bio, int cmd, long num, void *ptr)
+static long ossl_bio_cf_ctrl(BIO *bio, int cmd, long num, void *ptr)
{
struct Curl_cfilter *cf = BIO_get_data(bio);
long ret = 1;
@@ -721,7 +723,7 @@ static long bio_cf_ctrl(BIO *bio, int cmd, long num, void *ptr)
return ret;
}
-static int bio_cf_out_write(BIO *bio, const char *buf, int blen)
+static int ossl_bio_cf_out_write(BIO *bio, const char *buf, int blen)
{
struct Curl_cfilter *cf = BIO_get_data(bio);
struct ssl_connect_data *connssl = cf->ctx;
@@ -733,7 +735,7 @@ static int bio_cf_out_write(BIO *bio, const char *buf, int blen)
DEBUGASSERT(data);
nwritten = Curl_conn_cf_send(cf->next, data, buf, blen, &result);
- CURL_TRC_CF(data, cf, "bio_cf_out_write(len=%d) -> %d, err=%d",
+ CURL_TRC_CF(data, cf, "ossl_bio_cf_out_write(len=%d) -> %d, err=%d",
blen, (int)nwritten, result);
BIO_clear_retry_flags(bio);
backend->io_result = result;
@@ -744,7 +746,7 @@ static int bio_cf_out_write(BIO *bio, const char *buf, int blen)
return (int)nwritten;
}
-static int bio_cf_in_read(BIO *bio, char *buf, int blen)
+static int ossl_bio_cf_in_read(BIO *bio, char *buf, int blen)
{
struct Curl_cfilter *cf = BIO_get_data(bio);
struct ssl_connect_data *connssl = cf->ctx;
@@ -760,7 +762,7 @@ static int bio_cf_in_read(BIO *bio, char *buf, int blen)
return 0;
nread = Curl_conn_cf_recv(cf->next, data, buf, blen, &result);
- CURL_TRC_CF(data, cf, "bio_cf_in_read(len=%d) -> %d, err=%d",
+ CURL_TRC_CF(data, cf, "ossl_bio_cf_in_read(len=%d) -> %d, err=%d",
blen, (int)nread, result);
BIO_clear_retry_flags(bio);
backend->io_result = result;
@@ -785,42 +787,42 @@ static int bio_cf_in_read(BIO *bio, char *buf, int blen)
#if USE_PRE_1_1_API
-static BIO_METHOD bio_cf_meth_1_0 = {
+static BIO_METHOD ossl_bio_cf_meth_1_0 = {
BIO_TYPE_MEM,
"OpenSSL CF BIO",
- bio_cf_out_write,
- bio_cf_in_read,
+ ossl_bio_cf_out_write,
+ ossl_bio_cf_in_read,
NULL, /* puts is never called */
NULL, /* gets is never called */
- bio_cf_ctrl,
- bio_cf_create,
- bio_cf_destroy,
+ ossl_bio_cf_ctrl,
+ ossl_bio_cf_create,
+ ossl_bio_cf_destroy,
NULL
};
-static BIO_METHOD *bio_cf_method_create(void)
+static BIO_METHOD *ossl_bio_cf_method_create(void)
{
- return &bio_cf_meth_1_0;
+ return &ossl_bio_cf_meth_1_0;
}
-#define bio_cf_method_free(m) Curl_nop_stmt
+#define ossl_bio_cf_method_free(m) Curl_nop_stmt
#else
-static BIO_METHOD *bio_cf_method_create(void)
+static BIO_METHOD *ossl_bio_cf_method_create(void)
{
BIO_METHOD *m = BIO_meth_new(BIO_TYPE_MEM, "OpenSSL CF BIO");
if(m) {
- BIO_meth_set_write(m, &bio_cf_out_write);
- BIO_meth_set_read(m, &bio_cf_in_read);
- BIO_meth_set_ctrl(m, &bio_cf_ctrl);
- BIO_meth_set_create(m, &bio_cf_create);
- BIO_meth_set_destroy(m, &bio_cf_destroy);
+ BIO_meth_set_write(m, &ossl_bio_cf_out_write);
+ BIO_meth_set_read(m, &ossl_bio_cf_in_read);
+ BIO_meth_set_ctrl(m, &ossl_bio_cf_ctrl);
+ BIO_meth_set_create(m, &ossl_bio_cf_create);
+ BIO_meth_set_destroy(m, &ossl_bio_cf_destroy);
}
return m;
}
-static void bio_cf_method_free(BIO_METHOD *m)
+static void ossl_bio_cf_method_free(BIO_METHOD *m)
{
if(m)
BIO_meth_free(m);
@@ -1559,11 +1561,9 @@ fail:
UI_method_set_closer(ui_method, UI_method_get_closer(UI_OpenSSL()));
UI_method_set_reader(ui_method, ssl_ui_reader);
UI_method_set_writer(ui_method, ssl_ui_writer);
- /* the typecast below was added to please mingw32 */
- priv_key = (EVP_PKEY *)
- ENGINE_load_private_key(data->state.engine, key_file,
- ui_method,
- key_passwd);
+ priv_key = ENGINE_load_private_key(data->state.engine, key_file,
+ ui_method,
+ key_passwd);
UI_destroy_method(ui_method);
if(!priv_key) {
failf(data, "failed to load private key from crypto engine");
@@ -1886,15 +1886,45 @@ static void ossl_close(struct Curl_cfilter *cf, struct Curl_easy *data)
if(backend->handle) {
if(cf->next && cf->next->connected) {
- char buf[32];
+ char buf[1024];
+ int nread, err;
+ long sslerr;
+
/* Maybe the server has already sent a close notify alert.
Read it to avoid an RST on the TCP connection. */
(void)SSL_read(backend->handle, buf, (int)sizeof(buf));
-
- (void)SSL_shutdown(backend->handle);
-
ERR_clear_error();
+ if(SSL_shutdown(backend->handle) == 1) {
+ CURL_TRC_CF(data, cf, "SSL shutdown finished");
+ }
+ else {
+ nread = SSL_read(backend->handle, buf, (int)sizeof(buf));
+ err = SSL_get_error(backend->handle, nread);
+ switch(err) {
+ case SSL_ERROR_NONE: /* this is not an error */
+ case SSL_ERROR_ZERO_RETURN: /* no more data */
+ CURL_TRC_CF(data, cf, "SSL shutdown, EOF from server");
+ break;
+ case SSL_ERROR_WANT_READ:
+ /* SSL has send its notify and now wants to read the reply
+ * from the server. We are not really interested in that. */
+ CURL_TRC_CF(data, cf, "SSL shutdown sent");
+ break;
+ case SSL_ERROR_WANT_WRITE:
+ CURL_TRC_CF(data, cf, "SSL shutdown send blocked");
+ break;
+ default:
+ sslerr = ERR_get_error();
+ CURL_TRC_CF(data, cf, "SSL shutdown, error: '%s', errno %d",
+ (sslerr ?
+ ossl_strerror(sslerr, buf, sizeof(buf)) :
+ SSL_ERROR_to_str(err)),
+ SOCKERRNO);
+ break;
+ }
+ }
+ ERR_clear_error();
SSL_set_connect_state(backend->handle);
}
@@ -1907,7 +1937,7 @@ static void ossl_close(struct Curl_cfilter *cf, struct Curl_easy *data)
backend->x509_store_setup = FALSE;
}
if(backend->bio_method) {
- bio_cf_method_free(backend->bio_method);
+ ossl_bio_cf_method_free(backend->bio_method);
backend->bio_method = NULL;
}
}
@@ -3805,7 +3835,7 @@ static CURLcode ossl_connect_step1(struct Curl_cfilter *cf,
Curl_ssl_sessionid_unlock(data);
}
- backend->bio_method = bio_cf_method_create();
+ backend->bio_method = ossl_bio_cf_method_create();
if(!backend->bio_method)
return CURLE_OUT_OF_MEMORY;
bio = BIO_new(backend->bio_method);
diff --git a/Utilities/cmcurl/lib/vtls/schannel.c b/Utilities/cmcurl/lib/vtls/schannel.c
index f6a5d44..410a5c4 100644
--- a/Utilities/cmcurl/lib/vtls/schannel.c
+++ b/Utilities/cmcurl/lib/vtls/schannel.c
@@ -68,22 +68,6 @@
# define HAS_ALPN 1
#endif
-#ifndef UNISP_NAME_A
-#define UNISP_NAME_A "Microsoft Unified Security Protocol Provider"
-#endif
-
-#ifndef UNISP_NAME_W
-#define UNISP_NAME_W L"Microsoft Unified Security Protocol Provider"
-#endif
-
-#ifndef UNISP_NAME
-#ifdef UNICODE
-#define UNISP_NAME UNISP_NAME_W
-#else
-#define UNISP_NAME UNISP_NAME_A
-#endif
-#endif
-
#ifndef BCRYPT_CHACHA20_POLY1305_ALGORITHM
#define BCRYPT_CHACHA20_POLY1305_ALGORITHM L"CHACHA20_POLY1305"
#endif
@@ -108,13 +92,6 @@
#define BCRYPT_SHA384_ALGORITHM L"SHA384"
#endif
-/* Workaround broken compilers like MinGW.
- Return the number of elements in a statically sized array.
-*/
-#ifndef ARRAYSIZE
-#define ARRAYSIZE(A) (sizeof(A)/sizeof((A)[0]))
-#endif
-
#ifdef HAS_CLIENT_CERT_PATH
#ifdef UNICODE
#define CURL_CERT_STORE_PROV_SYSTEM CERT_STORE_PROV_SYSTEM_W
@@ -123,18 +100,6 @@
#endif
#endif
-#ifndef SP_PROT_SSL2_CLIENT
-#define SP_PROT_SSL2_CLIENT 0x00000008
-#endif
-
-#ifndef SP_PROT_SSL3_CLIENT
-#define SP_PROT_SSL3_CLIENT 0x00000008
-#endif
-
-#ifndef SP_PROT_TLS1_CLIENT
-#define SP_PROT_TLS1_CLIENT 0x00000080
-#endif
-
#ifndef SP_PROT_TLS1_0_CLIENT
#define SP_PROT_TLS1_0_CLIENT SP_PROT_TLS1_CLIENT
#endif
@@ -175,12 +140,6 @@
# define CALG_SHA_256 0x0000800c
#endif
-/* Work around typo in classic MinGW's w32api up to version 5.0,
- see https://osdn.net/projects/mingw/ticket/38391 */
-#if !defined(ALG_CLASS_DHASH) && defined(ALG_CLASS_HASH)
-#define ALG_CLASS_DHASH ALG_CLASS_HASH
-#endif
-
#ifndef PKCS12_NO_PERSIST_KEY
#define PKCS12_NO_PERSIST_KEY 0x00008000
#endif
@@ -769,7 +728,7 @@ schannel_acquire_credential_handle(struct Curl_cfilter *cf,
}
#endif
- /* allocate memory for the re-usable credential handle */
+ /* allocate memory for the reusable credential handle */
backend->cred = (struct Curl_schannel_cred *)
calloc(1, sizeof(struct Curl_schannel_cred));
if(!backend->cred) {
@@ -1169,7 +1128,7 @@ schannel_connect_step1(struct Curl_cfilter *cf, struct Curl_easy *data)
backend->cred = NULL;
- /* check for an existing re-usable credential handle */
+ /* check for an existing reusable credential handle */
if(ssl_config->primary.sessionid) {
Curl_ssl_sessionid_lock(data);
if(!Curl_ssl_getsessionid(cf, data, (void **)&old_cred, NULL)) {
@@ -2752,8 +2711,7 @@ static void schannel_checksum(const unsigned char *input,
if(!CryptCreateHash(hProv, algId, 0, 0, &hHash))
break; /* failed */
- /* workaround for original MinGW, should be (const BYTE*) */
- if(!CryptHashData(hHash, (BYTE*)input, (DWORD)inputlen, 0))
+ if(!CryptHashData(hHash, input, (DWORD)inputlen, 0))
break; /* failed */
/* get hash size */
diff --git a/Utilities/cmcurl/lib/vtls/schannel.h b/Utilities/cmcurl/lib/vtls/schannel.h
index be23567..b26334b 100644
--- a/Utilities/cmcurl/lib/vtls/schannel.h
+++ b/Utilities/cmcurl/lib/vtls/schannel.h
@@ -68,7 +68,7 @@
* BoringSSL's <openssl/x509.h>: So just undefine those defines here
* (and only here).
*/
-#if defined(HAVE_BORINGSSL) || defined(OPENSSL_IS_BORINGSSL)
+#if defined(OPENSSL_IS_BORINGSSL)
# undef X509_NAME
# undef X509_CERT_PAIR
# undef X509_EXTENSIONS
diff --git a/Utilities/cmcurl/lib/vtls/schannel_int.h b/Utilities/cmcurl/lib/vtls/schannel_int.h
index edb20bc..a128e04 100644
--- a/Utilities/cmcurl/lib/vtls/schannel_int.h
+++ b/Utilities/cmcurl/lib/vtls/schannel_int.h
@@ -28,15 +28,9 @@
#ifdef USE_SCHANNEL
-#ifdef __MINGW32__
-#ifdef __MINGW64_VERSION_MAJOR
+#if defined(__MINGW32__) || defined(CERT_CHAIN_REVOCATION_CHECK_CHAIN)
#define HAS_MANUAL_VERIFY_API
#endif
-#else
-#ifdef CERT_CHAIN_REVOCATION_CHECK_CHAIN
-#define HAS_MANUAL_VERIFY_API
-#endif
-#endif
#if defined(CryptStringToBinary) && defined(CRYPT_STRING_HEX) \
&& !defined(DISABLE_SCHANNEL_CLIENT_CERT)
@@ -60,41 +54,6 @@
#endif
-#if defined(__MINGW32__) && !defined(__MINGW64_VERSION_MAJOR)
-/* Original mingw is missing CERT structs or they're disabled.
- Refer to w32api-5.0.2-mingw32-dev\include\wincrypt.h. */
-
-/* !checksrc! disable TYPEDEFSTRUCT 4 */
-typedef struct _CERT_OTHER_NAME {
- LPSTR pszObjId;
- CRYPT_OBJID_BLOB Value;
-} CERT_OTHER_NAME, *PCERT_OTHER_NAME;
-
-typedef struct _CERT_ALT_NAME_ENTRY {
- DWORD dwAltNameChoice;
- union {
- PCERT_OTHER_NAME pOtherName;
- LPWSTR pwszRfc822Name;
- LPWSTR pwszDNSName;
- CERT_NAME_BLOB DirectoryName;
- LPWSTR pwszURL;
- CRYPT_DATA_BLOB IPAddress;
- LPSTR pszRegisteredID;
- };
-} CERT_ALT_NAME_ENTRY, *PCERT_ALT_NAME_ENTRY;
-
-typedef struct _CERT_ALT_NAME_INFO {
- DWORD cAltEntry;
- PCERT_ALT_NAME_ENTRY rgAltEntry;
-} CERT_ALT_NAME_INFO, *PCERT_ALT_NAME_INFO;
-
-typedef struct _CRYPT_DECODE_PARA {
- DWORD cbSize;
- PFN_CRYPT_ALLOC pfnAlloc;
- PFN_CRYPT_FREE pfnFree;
-} CRYPT_DECODE_PARA, *PCRYPT_DECODE_PARA;
-#endif
-
#ifndef SCH_CREDENTIALS_VERSION
#define SCH_CREDENTIALS_VERSION 0x00000005
diff --git a/Utilities/cmcurl/lib/vtls/sectransp.c b/Utilities/cmcurl/lib/vtls/sectransp.c
index e6a114a..3378f76 100644
--- a/Utilities/cmcurl/lib/vtls/sectransp.c
+++ b/Utilities/cmcurl/lib/vtls/sectransp.c
@@ -830,9 +830,9 @@ static const unsigned char ecDsaSecp384r1SpkiHeader[] = {
#endif /* SECTRANSP_PINNEDPUBKEY_V1 */
#endif /* SECTRANSP_PINNEDPUBKEY */
-static OSStatus bio_cf_in_read(SSLConnectionRef connection,
- void *buf,
- size_t *dataLength) /* IN/OUT */
+static OSStatus sectransp_bio_cf_in_read(SSLConnectionRef connection,
+ void *buf,
+ size_t *dataLength) /* IN/OUT */
{
struct Curl_cfilter *cf = (struct Curl_cfilter *)connection;
struct ssl_connect_data *connssl = cf->ctx;
@@ -870,9 +870,9 @@ static OSStatus bio_cf_in_read(SSLConnectionRef connection,
return rtn;
}
-static OSStatus bio_cf_out_write(SSLConnectionRef connection,
- const void *buf,
- size_t *dataLength) /* IN/OUT */
+static OSStatus sectransp_bio_cf_out_write(SSLConnectionRef connection,
+ const void *buf,
+ size_t *dataLength) /* IN/OUT */
{
struct Curl_cfilter *cf = (struct Curl_cfilter *)connection;
struct ssl_connect_data *connssl = cf->ctx;
@@ -2100,7 +2100,9 @@ static CURLcode sectransp_connect_step1(struct Curl_cfilter *cf,
}
}
- err = SSLSetIOFuncs(backend->ssl_ctx, bio_cf_in_read, bio_cf_out_write);
+ err = SSLSetIOFuncs(backend->ssl_ctx,
+ sectransp_bio_cf_in_read,
+ sectransp_bio_cf_out_write);
if(err != noErr) {
failf(data, "SSL: SSLSetIOFuncs() failed: OSStatus %d", err);
return CURLE_SSL_CONNECT_ERROR;
diff --git a/Utilities/cmcurl/lib/vtls/vtls.c b/Utilities/cmcurl/lib/vtls/vtls.c
index 38a20e8..494b660 100644
--- a/Utilities/cmcurl/lib/vtls/vtls.c
+++ b/Utilities/cmcurl/lib/vtls/vtls.c
@@ -1494,7 +1494,8 @@ static void ssl_cf_close(struct Curl_cfilter *cf,
CF_DATA_SAVE(save, cf, data);
cf_close(cf, data);
- cf->next->cft->do_close(cf->next, data);
+ if(cf->next)
+ cf->next->cft->do_close(cf->next, data);
CF_DATA_RESTORE(cf, save);
}
diff --git a/Utilities/cmcurl/lib/vtls/wolfssl.c b/Utilities/cmcurl/lib/vtls/wolfssl.c
index 5f15720..b1384a6 100644
--- a/Utilities/cmcurl/lib/vtls/wolfssl.c
+++ b/Utilities/cmcurl/lib/vtls/wolfssl.c
@@ -229,7 +229,7 @@ static const struct group_name_map gnm[] = {
#ifdef USE_BIO_CHAIN
-static int bio_cf_create(WOLFSSL_BIO *bio)
+static int wolfssl_bio_cf_create(WOLFSSL_BIO *bio)
{
wolfSSL_BIO_set_shutdown(bio, 1);
wolfSSL_BIO_set_init(bio, 1);
@@ -237,14 +237,14 @@ static int bio_cf_create(WOLFSSL_BIO *bio)
return 1;
}
-static int bio_cf_destroy(WOLFSSL_BIO *bio)
+static int wolfssl_bio_cf_destroy(WOLFSSL_BIO *bio)
{
if(!bio)
return 0;
return 1;
}
-static long bio_cf_ctrl(WOLFSSL_BIO *bio, int cmd, long num, void *ptr)
+static long wolfssl_bio_cf_ctrl(WOLFSSL_BIO *bio, int cmd, long num, void *ptr)
{
struct Curl_cfilter *cf = BIO_get_data(bio);
long ret = 1;
@@ -278,7 +278,8 @@ static long bio_cf_ctrl(WOLFSSL_BIO *bio, int cmd, long num, void *ptr)
return ret;
}
-static int bio_cf_out_write(WOLFSSL_BIO *bio, const char *buf, int blen)
+static int wolfssl_bio_cf_out_write(WOLFSSL_BIO *bio,
+ const char *buf, int blen)
{
struct Curl_cfilter *cf = wolfSSL_BIO_get_data(bio);
struct ssl_connect_data *connssl = cf->ctx;
@@ -299,7 +300,7 @@ static int bio_cf_out_write(WOLFSSL_BIO *bio, const char *buf, int blen)
return (int)nwritten;
}
-static int bio_cf_in_read(WOLFSSL_BIO *bio, char *buf, int blen)
+static int wolfssl_bio_cf_in_read(WOLFSSL_BIO *bio, char *buf, int blen)
{
struct Curl_cfilter *cf = wolfSSL_BIO_get_data(bio);
struct ssl_connect_data *connssl = cf->ctx;
@@ -323,27 +324,27 @@ static int bio_cf_in_read(WOLFSSL_BIO *bio, char *buf, int blen)
return (int)nread;
}
-static WOLFSSL_BIO_METHOD *bio_cf_method = NULL;
+static WOLFSSL_BIO_METHOD *wolfssl_bio_cf_method = NULL;
-static void bio_cf_init_methods(void)
+static void wolfssl_bio_cf_init_methods(void)
{
- bio_cf_method = wolfSSL_BIO_meth_new(BIO_TYPE_MEM, "wolfSSL CF BIO");
- wolfSSL_BIO_meth_set_write(bio_cf_method, &bio_cf_out_write);
- wolfSSL_BIO_meth_set_read(bio_cf_method, &bio_cf_in_read);
- wolfSSL_BIO_meth_set_ctrl(bio_cf_method, &bio_cf_ctrl);
- wolfSSL_BIO_meth_set_create(bio_cf_method, &bio_cf_create);
- wolfSSL_BIO_meth_set_destroy(bio_cf_method, &bio_cf_destroy);
+ wolfssl_bio_cf_method = wolfSSL_BIO_meth_new(BIO_TYPE_MEM, "wolfSSL CF BIO");
+ wolfSSL_BIO_meth_set_write(wolfssl_bio_cf_method, &wolfssl_bio_cf_out_write);
+ wolfSSL_BIO_meth_set_read(wolfssl_bio_cf_method, &wolfssl_bio_cf_in_read);
+ wolfSSL_BIO_meth_set_ctrl(wolfssl_bio_cf_method, &wolfssl_bio_cf_ctrl);
+ wolfSSL_BIO_meth_set_create(wolfssl_bio_cf_method, &wolfssl_bio_cf_create);
+ wolfSSL_BIO_meth_set_destroy(wolfssl_bio_cf_method, &wolfssl_bio_cf_destroy);
}
-static void bio_cf_free_methods(void)
+static void wolfssl_bio_cf_free_methods(void)
{
- wolfSSL_BIO_meth_free(bio_cf_method);
+ wolfSSL_BIO_meth_free(wolfssl_bio_cf_method);
}
#else /* USE_BIO_CHAIN */
-#define bio_cf_init_methods() Curl_nop_stmt
-#define bio_cf_free_methods() Curl_nop_stmt
+#define wolfssl_bio_cf_init_methods() Curl_nop_stmt
+#define wolfssl_bio_cf_free_methods() Curl_nop_stmt
#endif /* !USE_BIO_CHAIN */
@@ -361,6 +362,10 @@ wolfssl_connect_step1(struct Curl_cfilter *cf, struct Curl_easy *data)
struct ssl_primary_config *conn_config = Curl_ssl_cf_get_primary_config(cf);
const struct curl_blob *ca_info_blob = conn_config->ca_info_blob;
const struct ssl_config_data *ssl_config = Curl_ssl_cf_get_config(cf, data);
+ const char * const ssl_cafile =
+ /* CURLOPT_CAINFO_BLOB overrides CURLOPT_CAINFO */
+ (ca_info_blob ? NULL : conn_config->CAfile);
+ const char * const ssl_capath = conn_config->CApath;
WOLFSSL_METHOD* req_method = NULL;
#ifdef HAVE_LIBOQS
word16 oqsAlg = 0;
@@ -541,20 +546,21 @@ wolfssl_connect_step1(struct Curl_cfilter *cf, struct Curl_easy *data)
}
#ifndef NO_FILESYSTEM
- /* load trusted cacert */
- if(conn_config->CAfile) {
- if(1 != wolfSSL_CTX_load_verify_locations(backend->ctx,
- conn_config->CAfile,
- conn_config->CApath)) {
+ /* load trusted cacert from file if not blob */
+ if(ssl_cafile || ssl_capath) {
+ int rc =
+ wolfSSL_CTX_load_verify_locations_ex(backend->ctx,
+ ssl_cafile,
+ ssl_capath,
+ WOLFSSL_LOAD_FLAG_IGNORE_ERR);
+ if(SSL_SUCCESS != rc) {
if(conn_config->verifypeer && !imported_ca_info_blob &&
!imported_native_ca) {
/* Fail if we insist on successfully verifying the server. */
failf(data, "error setting certificate verify locations:"
" CAfile: %s CApath: %s",
- conn_config->CAfile?
- conn_config->CAfile: "none",
- conn_config->CApath?
- conn_config->CApath : "none");
+ ssl_cafile ? ssl_cafile : "none",
+ ssl_capath ? ssl_capath : "none");
return CURLE_SSL_CACERT_BADFILE;
}
else {
@@ -568,10 +574,8 @@ wolfssl_connect_step1(struct Curl_cfilter *cf, struct Curl_easy *data)
/* Everything is fine. */
infof(data, "successfully set certificate verify locations:");
}
- infof(data, " CAfile: %s",
- conn_config->CAfile ? conn_config->CAfile : "none");
- infof(data, " CApath: %s",
- conn_config->CApath ? conn_config->CApath : "none");
+ infof(data, " CAfile: %s", ssl_cafile ? ssl_cafile : "none");
+ infof(data, " CApath: %s", ssl_capath ? ssl_capath : "none");
}
/* Load the client certificate, and private key */
@@ -720,7 +724,7 @@ wolfssl_connect_step1(struct Curl_cfilter *cf, struct Curl_easy *data)
{
WOLFSSL_BIO *bio;
- bio = BIO_new(bio_cf_method);
+ bio = BIO_new(wolfssl_bio_cf_method);
if(!bio)
return CURLE_OUT_OF_MEMORY;
@@ -1140,14 +1144,14 @@ static int wolfssl_init(void)
Curl_tls_keylog_open();
#endif
ret = (wolfSSL_Init() == SSL_SUCCESS);
- bio_cf_init_methods();
+ wolfssl_bio_cf_init_methods();
return ret;
}
static void wolfssl_cleanup(void)
{
- bio_cf_free_methods();
+ wolfssl_bio_cf_free_methods();
wolfSSL_Cleanup();
#ifdef OPENSSL_EXTRA
Curl_tls_keylog_close();
@@ -1378,6 +1382,7 @@ const struct Curl_ssl Curl_ssl_wolfssl = {
#ifdef USE_BIO_CHAIN
SSLSUPP_HTTPS_PROXY |
#endif
+ SSLSUPP_CA_PATH |
SSLSUPP_CAINFO_BLOB |
SSLSUPP_SSL_CTX,
diff --git a/Utilities/cmcurl/lib/warnless.c b/Utilities/cmcurl/lib/warnless.c
index 65c5ec5..7e077f8 100644
--- a/Utilities/cmcurl/lib/warnless.c
+++ b/Utilities/cmcurl/lib/warnless.c
@@ -384,54 +384,3 @@ ssize_t curlx_write(int fd, const void *buf, size_t count)
#endif /* WIN32 */
-#if defined(__INTEL_COMPILER) && defined(__unix__)
-
-int curlx_FD_ISSET(int fd, fd_set *fdset)
-{
- #pragma warning(push)
- #pragma warning(disable:1469) /* clobber ignored */
- return FD_ISSET(fd, fdset);
- #pragma warning(pop)
-}
-
-void curlx_FD_SET(int fd, fd_set *fdset)
-{
- #pragma warning(push)
- #pragma warning(disable:1469) /* clobber ignored */
- FD_SET(fd, fdset);
- #pragma warning(pop)
-}
-
-void curlx_FD_ZERO(fd_set *fdset)
-{
- #pragma warning(push)
- #pragma warning(disable:593) /* variable was set but never used */
- FD_ZERO(fdset);
- #pragma warning(pop)
-}
-
-unsigned short curlx_htons(unsigned short usnum)
-{
-#if (__INTEL_COMPILER == 910) && defined(__i386__)
- return (unsigned short)(((usnum << 8) & 0xFF00) | ((usnum >> 8) & 0x00FF));
-#else
- #pragma warning(push)
- #pragma warning(disable:810) /* conversion may lose significant bits */
- return htons(usnum);
- #pragma warning(pop)
-#endif
-}
-
-unsigned short curlx_ntohs(unsigned short usnum)
-{
-#if (__INTEL_COMPILER == 910) && defined(__i386__)
- return (unsigned short)(((usnum << 8) & 0xFF00) | ((usnum >> 8) & 0x00FF));
-#else
- #pragma warning(push)
- #pragma warning(disable:810) /* conversion may lose significant bits */
- return ntohs(usnum);
- #pragma warning(pop)
-#endif
-}
-
-#endif /* __INTEL_COMPILER && __unix__ */