mirror of
https://github.com/cmclark00/retro-imager.git
synced 2025-05-18 16:05:21 +01:00
Windows: update libcurl dependency
Update bundled libcurl. Only used on Windows. On Linux and OSX we use system libraries.
This commit is contained in:
parent
a97de5c703
commit
0378751295
370 changed files with 68199 additions and 38210 deletions
1
src/dependencies/cmcurl/.gitattributes
vendored
Normal file
1
src/dependencies/cmcurl/.gitattributes
vendored
Normal file
|
@ -0,0 +1 @@
|
|||
* -whitespace
|
|
@ -1 +1,24 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
@CMAKE_CONFIGURABLE_FILE_CONTENT@
|
||||
|
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
include(CheckCSourceCompiles)
|
||||
|
||||
option(CURL_HIDDEN_SYMBOLS "Set to ON to hide libcurl internal symbols (=hide all symbols that aren't officially external)." ON)
|
||||
|
@ -6,18 +29,12 @@ mark_as_advanced(CURL_HIDDEN_SYMBOLS)
|
|||
if(CURL_HIDDEN_SYMBOLS)
|
||||
set(SUPPORTS_SYMBOL_HIDING FALSE)
|
||||
|
||||
if(CMAKE_C_COMPILER_ID MATCHES "Clang")
|
||||
if(CMAKE_C_COMPILER_ID MATCHES "Clang" AND NOT MSVC)
|
||||
set(SUPPORTS_SYMBOL_HIDING TRUE)
|
||||
set(_SYMBOL_EXTERN "__attribute__ ((__visibility__ (\"default\")))")
|
||||
set(_CFLAG_SYMBOLS_HIDE "-fvisibility=hidden")
|
||||
elseif(CMAKE_COMPILER_IS_GNUCC)
|
||||
if(NOT CMAKE_VERSION VERSION_LESS 2.8.10)
|
||||
set(GCC_VERSION ${CMAKE_C_COMPILER_VERSION})
|
||||
else()
|
||||
execute_process(COMMAND ${CMAKE_C_COMPILER} -dumpversion
|
||||
OUTPUT_VARIABLE GCC_VERSION)
|
||||
endif()
|
||||
if(NOT GCC_VERSION VERSION_LESS 3.4)
|
||||
if(NOT CMAKE_C_COMPILER_VERSION VERSION_LESS 3.4)
|
||||
# note: this is considered buggy prior to 4.0 but the autotools don't care, so let's ignore that fact
|
||||
set(SUPPORTS_SYMBOL_HIDING TRUE)
|
||||
set(_SYMBOL_EXTERN "__attribute__ ((__visibility__ (\"default\")))")
|
||||
|
@ -29,7 +46,7 @@ if(CURL_HIDDEN_SYMBOLS)
|
|||
set(_CFLAG_SYMBOLS_HIDE "-xldscope=hidden")
|
||||
elseif(CMAKE_C_COMPILER_ID MATCHES "Intel" AND NOT CMAKE_C_COMPILER_VERSION VERSION_LESS 9.0)
|
||||
# note: this should probably just check for version 9.1.045 but I'm not 100% sure
|
||||
# so let's to it the same way autotools do.
|
||||
# so let's do it the same way autotools do.
|
||||
set(SUPPORTS_SYMBOL_HIDING TRUE)
|
||||
set(_SYMBOL_EXTERN "__attribute__ ((__visibility__ (\"default\")))")
|
||||
set(_CFLAG_SYMBOLS_HIDE "-fvisibility=hidden")
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2014, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#ifdef TIME_WITH_SYS_TIME
|
||||
/* Time with sys/time test */
|
||||
|
@ -56,7 +58,7 @@ return 0;
|
|||
# define PLATFORM_AIX_V3
|
||||
#endif
|
||||
/* */
|
||||
#if defined(PLATFORM_SUNOS4) || defined(PLATFORM_AIX_V3) || defined(__BEOS__)
|
||||
#if defined(PLATFORM_SUNOS4) || defined(PLATFORM_AIX_V3)
|
||||
#error "O_NONBLOCK does not work on this platform"
|
||||
#endif
|
||||
|
||||
|
@ -71,21 +73,15 @@ main ()
|
|||
}
|
||||
#endif
|
||||
|
||||
/* tests for gethostbyaddr_r or gethostbyname_r */
|
||||
#if defined(HAVE_GETHOSTBYADDR_R_5_REENTRANT) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_7_REENTRANT) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_8_REENTRANT) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_3_REENTRANT) || \
|
||||
/* tests for gethostbyname_r */
|
||||
#if defined(HAVE_GETHOSTBYNAME_R_3_REENTRANT) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_5_REENTRANT) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_6_REENTRANT)
|
||||
# define _REENTRANT
|
||||
/* no idea whether _REENTRANT is always set, just invent a new flag */
|
||||
# define TEST_GETHOSTBYFOO_REENTRANT
|
||||
#endif
|
||||
#if defined(HAVE_GETHOSTBYADDR_R_5) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_7) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_8) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_3) || \
|
||||
#if defined(HAVE_GETHOSTBYNAME_R_3) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_5) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_6) || \
|
||||
defined(TEST_GETHOSTBYFOO_REENTRANT)
|
||||
|
@ -98,18 +94,10 @@ int main(void)
|
|||
int type = 0;
|
||||
struct hostent h;
|
||||
int rc = 0;
|
||||
#if defined(HAVE_GETHOSTBYADDR_R_5) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_5_REENTRANT) || \
|
||||
\
|
||||
defined(HAVE_GETHOSTBYNAME_R_3) || \
|
||||
#if defined(HAVE_GETHOSTBYNAME_R_3) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_3_REENTRANT)
|
||||
struct hostent_data hdata;
|
||||
#elif defined(HAVE_GETHOSTBYADDR_R_7) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_7_REENTRANT) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_8) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_8_REENTRANT) || \
|
||||
\
|
||||
defined(HAVE_GETHOSTBYNAME_R_5) || \
|
||||
#elif defined(HAVE_GETHOSTBYNAME_R_5) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_5_REENTRANT) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_6) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_6_REENTRANT)
|
||||
|
@ -118,22 +106,6 @@ int main(void)
|
|||
struct hostent *hp;
|
||||
#endif
|
||||
|
||||
#ifndef gethostbyaddr_r
|
||||
(void)gethostbyaddr_r;
|
||||
#endif
|
||||
|
||||
#if defined(HAVE_GETHOSTBYADDR_R_5) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_5_REENTRANT)
|
||||
rc = gethostbyaddr_r(address, length, type, &h, &hdata);
|
||||
#elif defined(HAVE_GETHOSTBYADDR_R_7) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_7_REENTRANT)
|
||||
hp = gethostbyaddr_r(address, length, type, &h, buffer, 8192, &h_errnop);
|
||||
(void)hp;
|
||||
#elif defined(HAVE_GETHOSTBYADDR_R_8) || \
|
||||
defined(HAVE_GETHOSTBYADDR_R_8_REENTRANT)
|
||||
rc = gethostbyaddr_r(address, length, type, &h, buffer, 8192, &hp, &h_errnop);
|
||||
#endif
|
||||
|
||||
#if defined(HAVE_GETHOSTBYNAME_R_3) || \
|
||||
defined(HAVE_GETHOSTBYNAME_R_3_REENTRANT)
|
||||
rc = gethostbyname_r(address, &h, &hdata);
|
||||
|
@ -212,77 +184,6 @@ if (sizeof (bool *) )
|
|||
#include <float.h>
|
||||
int main() { return 0; }
|
||||
#endif
|
||||
#ifdef RETSIGTYPE_TEST
|
||||
#include <sys/types.h>
|
||||
#include <signal.h>
|
||||
#ifdef signal
|
||||
# undef signal
|
||||
#endif
|
||||
#ifdef __cplusplus
|
||||
extern "C" void (*signal (int, void (*)(int)))(int);
|
||||
#else
|
||||
void (*signal ()) ();
|
||||
#endif
|
||||
|
||||
int
|
||||
main ()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
#ifdef HAVE_INET_NTOA_R_DECL
|
||||
#include <arpa/inet.h>
|
||||
|
||||
typedef void (*func_type)();
|
||||
|
||||
int main()
|
||||
{
|
||||
#ifndef inet_ntoa_r
|
||||
func_type func;
|
||||
func = (func_type)inet_ntoa_r;
|
||||
(void)func;
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
#ifdef HAVE_INET_NTOA_R_DECL_REENTRANT
|
||||
#define _REENTRANT
|
||||
#include <arpa/inet.h>
|
||||
|
||||
typedef void (*func_type)();
|
||||
|
||||
int main()
|
||||
{
|
||||
#ifndef inet_ntoa_r
|
||||
func_type func;
|
||||
func = (func_type)&inet_ntoa_r;
|
||||
(void)func;
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
#ifdef HAVE_GETADDRINFO
|
||||
#include <netdb.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/socket.h>
|
||||
|
||||
int main(void) {
|
||||
struct addrinfo hints, *ai;
|
||||
int error;
|
||||
|
||||
memset(&hints, 0, sizeof(hints));
|
||||
hints.ai_family = AF_UNSPEC;
|
||||
hints.ai_socktype = SOCK_STREAM;
|
||||
#ifndef getaddrinfo
|
||||
(void)getaddrinfo;
|
||||
#endif
|
||||
error = getaddrinfo("127.0.0.1", "8080", &hints, &ai);
|
||||
if (error) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
#ifdef HAVE_FILE_OFFSET_BITS
|
||||
#ifdef _FILE_OFFSET_BITS
|
||||
#undef _FILE_OFFSET_BITS
|
||||
|
@ -308,10 +209,6 @@ int main () { ; return 0; }
|
|||
# include <windows.h>
|
||||
# ifdef HAVE_WINSOCK2_H
|
||||
# include <winsock2.h>
|
||||
# else
|
||||
# ifdef HAVE_WINSOCK_H
|
||||
# include <winsock.h>
|
||||
# endif
|
||||
# endif
|
||||
#endif
|
||||
|
||||
|
@ -337,10 +234,6 @@ main ()
|
|||
# include <windows.h>
|
||||
# ifdef HAVE_WINSOCK2_H
|
||||
# include <winsock2.h>
|
||||
# else
|
||||
# ifdef HAVE_WINSOCK_H
|
||||
# include <winsock.h>
|
||||
# endif
|
||||
# endif
|
||||
#endif
|
||||
|
||||
|
@ -364,10 +257,6 @@ main ()
|
|||
# include <windows.h>
|
||||
# ifdef HAVE_WINSOCK2_H
|
||||
# include <winsock2.h>
|
||||
# else
|
||||
# ifdef HAVE_WINSOCK_H
|
||||
# include <winsock.h>
|
||||
# endif
|
||||
# endif
|
||||
#endif
|
||||
|
||||
|
@ -377,7 +266,7 @@ main ()
|
|||
|
||||
/* IoctlSocket source code */
|
||||
long flags = 0;
|
||||
if(0 != ioctlsocket(0, FIONBIO, &flags))
|
||||
if(0 != IoctlSocket(0, FIONBIO, &flags))
|
||||
return 1;
|
||||
;
|
||||
return 0;
|
||||
|
@ -392,10 +281,6 @@ main ()
|
|||
# include <windows.h>
|
||||
# ifdef HAVE_WINSOCK2_H
|
||||
# include <winsock2.h>
|
||||
# else
|
||||
# ifdef HAVE_WINSOCK_H
|
||||
# include <winsock.h>
|
||||
# endif
|
||||
# endif
|
||||
#endif
|
||||
|
||||
|
@ -482,10 +367,6 @@ main ()
|
|||
# include <windows.h>
|
||||
# ifdef HAVE_WINSOCK2_H
|
||||
# include <winsock2.h>
|
||||
# else
|
||||
# ifdef HAVE_WINSOCK_H
|
||||
# include <winsock.h>
|
||||
# endif
|
||||
# endif
|
||||
#endif
|
||||
/* includes start */
|
||||
|
@ -613,3 +494,39 @@ main() {
|
|||
return 0;
|
||||
}
|
||||
#endif
|
||||
#ifdef HAVE_ATOMIC
|
||||
/* includes start */
|
||||
#ifdef HAVE_SYS_TYPES_H
|
||||
# include <sys/types.h>
|
||||
#endif
|
||||
#ifdef HAVE_UNISTD_H
|
||||
# include <unistd.h>
|
||||
#endif
|
||||
#ifdef HAVE_STDATOMIC_H
|
||||
# include <stdatomic.h>
|
||||
#endif
|
||||
/* includes end */
|
||||
|
||||
int
|
||||
main() {
|
||||
_Atomic int i = 1;
|
||||
i = 0; // Force an atomic-write operation.
|
||||
return i;
|
||||
}
|
||||
#endif
|
||||
#ifdef HAVE_WIN32_WINNT
|
||||
/* includes start */
|
||||
#ifdef WIN32
|
||||
# include "../lib/setup-win32.h"
|
||||
#endif
|
||||
/* includes end */
|
||||
|
||||
#define enquote(x) #x
|
||||
#define expand(x) enquote(x)
|
||||
#pragma message("_WIN32_WINNT=" expand(_WIN32_WINNT))
|
||||
|
||||
int
|
||||
main() {
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
|
32
src/dependencies/cmcurl/CMake/FindBearSSL.cmake
Normal file
32
src/dependencies/cmcurl/CMake/FindBearSSL.cmake
Normal file
|
@ -0,0 +1,32 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
find_path(BEARSSL_INCLUDE_DIRS bearssl.h)
|
||||
|
||||
find_library(BEARSSL_LIBRARY bearssl)
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(BEARSSL DEFAULT_MSG
|
||||
BEARSSL_INCLUDE_DIRS BEARSSL_LIBRARY)
|
||||
|
||||
mark_as_advanced(BEARSSL_INCLUDE_DIRS BEARSSL_LIBRARY)
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
include(FindPackageHandleStandardArgs)
|
||||
|
||||
find_path(BROTLI_INCLUDE_DIR "brotli/decode.h")
|
||||
|
@ -5,7 +28,7 @@ find_path(BROTLI_INCLUDE_DIR "brotli/decode.h")
|
|||
find_library(BROTLICOMMON_LIBRARY NAMES brotlicommon)
|
||||
find_library(BROTLIDEC_LIBRARY NAMES brotlidec)
|
||||
|
||||
find_package_handle_standard_args(BROTLI
|
||||
find_package_handle_standard_args(Brotli
|
||||
FOUND_VAR
|
||||
BROTLI_FOUND
|
||||
REQUIRED_VARS
|
||||
|
@ -13,7 +36,7 @@ find_package_handle_standard_args(BROTLI
|
|||
BROTLICOMMON_LIBRARY
|
||||
BROTLI_INCLUDE_DIR
|
||||
FAIL_MESSAGE
|
||||
"Could NOT find BROTLI"
|
||||
"Could NOT find Brotli"
|
||||
)
|
||||
|
||||
set(BROTLI_INCLUDE_DIRS ${BROTLI_INCLUDE_DIR})
|
||||
|
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
# - Find c-ares
|
||||
# Find the c-ares includes and library
|
||||
# This module defines
|
||||
|
@ -7,34 +30,16 @@
|
|||
# also defined, but not for general use are
|
||||
# CARES_LIBRARY, where to find the c-ares library.
|
||||
|
||||
find_path(CARES_INCLUDE_DIR ares.h
|
||||
/usr/local/include
|
||||
/usr/include
|
||||
)
|
||||
find_path(CARES_INCLUDE_DIR ares.h)
|
||||
|
||||
set(CARES_NAMES ${CARES_NAMES} cares)
|
||||
find_library(CARES_LIBRARY
|
||||
NAMES ${CARES_NAMES}
|
||||
PATHS /usr/lib /usr/local/lib
|
||||
)
|
||||
|
||||
if(CARES_LIBRARY AND CARES_INCLUDE_DIR)
|
||||
set(CARES_LIBRARIES ${CARES_LIBRARY})
|
||||
set(CARES_FOUND "YES")
|
||||
else()
|
||||
set(CARES_FOUND "NO")
|
||||
endif()
|
||||
|
||||
|
||||
if(CARES_FOUND)
|
||||
if(NOT CARES_FIND_QUIETLY)
|
||||
message(STATUS "Found c-ares: ${CARES_LIBRARIES}")
|
||||
endif()
|
||||
else()
|
||||
if(CARES_FIND_REQUIRED)
|
||||
message(FATAL_ERROR "Could not find c-ares library")
|
||||
endif()
|
||||
endif()
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(CARES
|
||||
REQUIRED_VARS CARES_LIBRARY CARES_INCLUDE_DIR)
|
||||
|
||||
mark_as_advanced(
|
||||
CARES_LIBRARY
|
||||
|
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
# - Try to find the GSS Kerberos library
|
||||
# Once done this will define
|
||||
#
|
||||
|
@ -62,6 +85,7 @@ if(NOT _GSS_FOUND) #not found by pkg-config. Let's take more traditional approac
|
|||
COMMAND ${_GSS_CONFIGURE_SCRIPT} "--cflags" "gssapi"
|
||||
OUTPUT_VARIABLE _GSS_CFLAGS
|
||||
RESULT_VARIABLE _GSS_CONFIGURE_FAILED
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
)
|
||||
message(STATUS "CFLAGS: ${_GSS_CFLAGS}")
|
||||
if(NOT _GSS_CONFIGURE_FAILED) # 0 means success
|
||||
|
@ -84,6 +108,7 @@ if(NOT _GSS_FOUND) #not found by pkg-config. Let's take more traditional approac
|
|||
COMMAND ${_GSS_CONFIGURE_SCRIPT} "--libs" "gssapi"
|
||||
OUTPUT_VARIABLE _GSS_LIB_FLAGS
|
||||
RESULT_VARIABLE _GSS_CONFIGURE_FAILED
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
)
|
||||
message(STATUS "LDFLAGS: ${_GSS_LIB_FLAGS}")
|
||||
|
||||
|
@ -110,6 +135,7 @@ if(NOT _GSS_FOUND) #not found by pkg-config. Let's take more traditional approac
|
|||
COMMAND ${_GSS_CONFIGURE_SCRIPT} "--version"
|
||||
OUTPUT_VARIABLE _GSS_VERSION
|
||||
RESULT_VARIABLE _GSS_CONFIGURE_FAILED
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
)
|
||||
|
||||
# older versions may not have the "--version" parameter. In this case we just don't care.
|
||||
|
@ -121,6 +147,7 @@ if(NOT _GSS_FOUND) #not found by pkg-config. Let's take more traditional approac
|
|||
COMMAND ${_GSS_CONFIGURE_SCRIPT} "--vendor"
|
||||
OUTPUT_VARIABLE _GSS_VENDOR
|
||||
RESULT_VARIABLE _GSS_CONFIGURE_FAILED
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
)
|
||||
|
||||
# older versions may not have the "--vendor" parameter. In this case we just don't care.
|
||||
|
@ -134,7 +161,7 @@ if(NOT _GSS_FOUND) #not found by pkg-config. Let's take more traditional approac
|
|||
endif()
|
||||
endif()
|
||||
|
||||
else() # either there is no config script or we are on platform that doesn't provide one (Windows?)
|
||||
else() # either there is no config script or we are on a platform that doesn't provide one (Windows?)
|
||||
|
||||
find_path(_GSS_INCLUDE_DIR
|
||||
NAMES
|
||||
|
@ -154,17 +181,17 @@ if(NOT _GSS_FOUND) #not found by pkg-config. Let's take more traditional approac
|
|||
set(GSS_FLAVOUR "MIT")
|
||||
else()
|
||||
# prevent compiling the header - just check if we can include it
|
||||
set(CMAKE_REQUIRED_DEFINITIONS "${CMAKE_REQUIRED_DEFINITIONS} -D__ROKEN_H__")
|
||||
list(APPEND CMAKE_REQUIRED_DEFINITIONS -D__ROKEN_H__)
|
||||
check_include_file( "roken.h" _GSS_HAVE_ROKEN_H)
|
||||
|
||||
check_include_file( "heimdal/roken.h" _GSS_HAVE_HEIMDAL_ROKEN_H)
|
||||
if(_GSS_HAVE_ROKEN_H OR _GSS_HAVE_HEIMDAL_ROKEN_H)
|
||||
set(GSS_FLAVOUR "Heimdal")
|
||||
endif()
|
||||
set(CMAKE_REQUIRED_DEFINITIONS "")
|
||||
list(REMOVE_ITEM CMAKE_REQUIRED_DEFINITIONS -D__ROKEN_H__)
|
||||
endif()
|
||||
else()
|
||||
# I'm not convienced if this is the right way but this is what autotools do at the moment
|
||||
# I'm not convinced if this is the right way but this is what autotools do at the moment
|
||||
find_path(_GSS_INCLUDE_DIR
|
||||
NAMES
|
||||
"gssapi.h"
|
||||
|
|
45
src/dependencies/cmcurl/CMake/FindLibPSL.cmake
Normal file
45
src/dependencies/cmcurl/CMake/FindLibPSL.cmake
Normal file
|
@ -0,0 +1,45 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
# - Try to find the libpsl library
|
||||
# Once done this will define
|
||||
#
|
||||
# LIBPSL_FOUND - system has the libpsl library
|
||||
# LIBPSL_INCLUDE_DIR - the libpsl include directory
|
||||
# LIBPSL_LIBRARY - the libpsl library name
|
||||
|
||||
find_path(LIBPSL_INCLUDE_DIR libpsl.h)
|
||||
|
||||
find_library(LIBPSL_LIBRARY NAMES psl libpsl)
|
||||
|
||||
if(LIBPSL_INCLUDE_DIR)
|
||||
file(STRINGS "${LIBPSL_INCLUDE_DIR}/libpsl.h" libpsl_version_str REGEX "^#define[\t ]+PSL_VERSION[\t ]+\"(.*)\"")
|
||||
string(REGEX REPLACE "^.*\"([^\"]+)\"" "\\1" LIBPSL_VERSION "${libpsl_version_str}")
|
||||
endif()
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(LibPSL
|
||||
REQUIRED_VARS LIBPSL_LIBRARY LIBPSL_INCLUDE_DIR
|
||||
VERSION_VAR LIBPSL_VERSION)
|
||||
|
||||
mark_as_advanced(LIBPSL_INCLUDE_DIR LIBPSL_LIBRARY)
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
# - Try to find the libssh2 library
|
||||
# Once done this will define
|
||||
#
|
||||
|
@ -5,31 +28,18 @@
|
|||
# LIBSSH2_INCLUDE_DIR - the libssh2 include directory
|
||||
# LIBSSH2_LIBRARY - the libssh2 library name
|
||||
|
||||
if(LIBSSH2_INCLUDE_DIR AND LIBSSH2_LIBRARY)
|
||||
set(LibSSH2_FIND_QUIETLY TRUE)
|
||||
endif()
|
||||
find_path(LIBSSH2_INCLUDE_DIR libssh2.h)
|
||||
|
||||
find_path(LIBSSH2_INCLUDE_DIR libssh2.h
|
||||
)
|
||||
|
||||
find_library(LIBSSH2_LIBRARY NAMES ssh2
|
||||
)
|
||||
find_library(LIBSSH2_LIBRARY NAMES ssh2 libssh2)
|
||||
|
||||
if(LIBSSH2_INCLUDE_DIR)
|
||||
file(STRINGS "${LIBSSH2_INCLUDE_DIR}/libssh2.h" libssh2_version_str REGEX "^#define[\t ]+LIBSSH2_VERSION_NUM[\t ]+0x[0-9][0-9][0-9][0-9][0-9][0-9].*")
|
||||
|
||||
string(REGEX REPLACE "^.*LIBSSH2_VERSION_NUM[\t ]+0x([0-9][0-9]).*$" "\\1" LIBSSH2_VERSION_MAJOR "${libssh2_version_str}")
|
||||
string(REGEX REPLACE "^.*LIBSSH2_VERSION_NUM[\t ]+0x[0-9][0-9]([0-9][0-9]).*$" "\\1" LIBSSH2_VERSION_MINOR "${libssh2_version_str}")
|
||||
string(REGEX REPLACE "^.*LIBSSH2_VERSION_NUM[\t ]+0x[0-9][0-9][0-9][0-9]([0-9][0-9]).*$" "\\1" LIBSSH2_VERSION_PATCH "${libssh2_version_str}")
|
||||
|
||||
string(REGEX REPLACE "^0(.+)" "\\1" LIBSSH2_VERSION_MAJOR "${LIBSSH2_VERSION_MAJOR}")
|
||||
string(REGEX REPLACE "^0(.+)" "\\1" LIBSSH2_VERSION_MINOR "${LIBSSH2_VERSION_MINOR}")
|
||||
string(REGEX REPLACE "^0(.+)" "\\1" LIBSSH2_VERSION_PATCH "${LIBSSH2_VERSION_PATCH}")
|
||||
|
||||
set(LIBSSH2_VERSION "${LIBSSH2_VERSION_MAJOR}.${LIBSSH2_VERSION_MINOR}.${LIBSSH2_VERSION_PATCH}")
|
||||
file(STRINGS "${LIBSSH2_INCLUDE_DIR}/libssh2.h" libssh2_version_str REGEX "^#define[\t ]+LIBSSH2_VERSION[\t ]+\"(.*)\"")
|
||||
string(REGEX REPLACE "^.*\"([^\"]+)\"" "\\1" LIBSSH2_VERSION "${libssh2_version_str}")
|
||||
endif()
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(LibSSH2 DEFAULT_MSG LIBSSH2_INCLUDE_DIR LIBSSH2_LIBRARY )
|
||||
find_package_handle_standard_args(LibSSH2
|
||||
REQUIRED_VARS LIBSSH2_LIBRARY LIBSSH2_INCLUDE_DIR
|
||||
VERSION_VAR LIBSSH2_VERSION)
|
||||
|
||||
mark_as_advanced(LIBSSH2_INCLUDE_DIR LIBSSH2_LIBRARY LIBSSH2_VERSION_MAJOR LIBSSH2_VERSION_MINOR LIBSSH2_VERSION_PATCH LIBSSH2_VERSION)
|
||||
mark_as_advanced(LIBSSH2_INCLUDE_DIR LIBSSH2_LIBRARY)
|
||||
|
|
70
src/dependencies/cmcurl/CMake/FindMSH3.cmake
Normal file
70
src/dependencies/cmcurl/CMake/FindMSH3.cmake
Normal file
|
@ -0,0 +1,70 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
|
||||
#[=======================================================================[.rst:
|
||||
FindMSH3
|
||||
----------
|
||||
|
||||
Find the msh3 library
|
||||
|
||||
Result Variables
|
||||
^^^^^^^^^^^^^^^^
|
||||
|
||||
``MSH3_FOUND``
|
||||
System has msh3
|
||||
``MSH3_INCLUDE_DIRS``
|
||||
The msh3 include directories.
|
||||
``MSH3_LIBRARIES``
|
||||
The libraries needed to use msh3
|
||||
#]=======================================================================]
|
||||
if(UNIX)
|
||||
find_package(PkgConfig QUIET)
|
||||
pkg_search_module(PC_MSH3 libmsh3)
|
||||
endif()
|
||||
|
||||
find_path(MSH3_INCLUDE_DIR msh3.h
|
||||
HINTS
|
||||
${PC_MSH3_INCLUDEDIR}
|
||||
${PC_MSH3_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
find_library(MSH3_LIBRARY NAMES msh3
|
||||
HINTS
|
||||
${PC_MSH3_LIBDIR}
|
||||
${PC_MSH3_LIBRARY_DIRS}
|
||||
)
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(MSH3
|
||||
REQUIRED_VARS
|
||||
MSH3_LIBRARY
|
||||
MSH3_INCLUDE_DIR
|
||||
)
|
||||
|
||||
if(MSH3_FOUND)
|
||||
set(MSH3_LIBRARIES ${MSH3_LIBRARY})
|
||||
set(MSH3_INCLUDE_DIRS ${MSH3_INCLUDE_DIR})
|
||||
endif()
|
||||
|
||||
mark_as_advanced(MSH3_INCLUDE_DIRS MSH3_LIBRARIES)
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
find_path(MBEDTLS_INCLUDE_DIRS mbedtls/ssl.h)
|
||||
|
||||
find_library(MBEDTLS_LIBRARY mbedtls)
|
||||
|
@ -7,7 +30,7 @@ find_library(MBEDCRYPTO_LIBRARY mbedcrypto)
|
|||
set(MBEDTLS_LIBRARIES "${MBEDTLS_LIBRARY}" "${MBEDX509_LIBRARY}" "${MBEDCRYPTO_LIBRARY}")
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(MBEDTLS DEFAULT_MSG
|
||||
find_package_handle_standard_args(MbedTLS DEFAULT_MSG
|
||||
MBEDTLS_INCLUDE_DIRS MBEDTLS_LIBRARY MBEDX509_LIBRARY MBEDCRYPTO_LIBRARY)
|
||||
|
||||
mark_as_advanced(MBEDTLS_INCLUDE_DIRS MBEDTLS_LIBRARY MBEDX509_LIBRARY MBEDCRYPTO_LIBRARY)
|
||||
|
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
include(FindPackageHandleStandardArgs)
|
||||
|
||||
find_path(NGHTTP2_INCLUDE_DIR "nghttp2/nghttp2.h")
|
||||
|
@ -10,9 +33,9 @@ find_package_handle_standard_args(NGHTTP2
|
|||
REQUIRED_VARS
|
||||
NGHTTP2_LIBRARY
|
||||
NGHTTP2_INCLUDE_DIR
|
||||
FAIL_MESSAGE
|
||||
"Could NOT find NGHTTP2"
|
||||
)
|
||||
|
||||
set(NGHTTP2_INCLUDE_DIRS ${NGHTTP2_INCLUDE_DIR})
|
||||
set(NGHTTP2_LIBRARIES ${NGHTTP2_LIBRARY})
|
||||
|
||||
mark_as_advanced(NGHTTP2_INCLUDE_DIRS NGHTTP2_LIBRARIES)
|
||||
|
|
78
src/dependencies/cmcurl/CMake/FindNGHTTP3.cmake
Normal file
78
src/dependencies/cmcurl/CMake/FindNGHTTP3.cmake
Normal file
|
@ -0,0 +1,78 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
|
||||
#[=======================================================================[.rst:
|
||||
FindNGHTTP3
|
||||
----------
|
||||
|
||||
Find the nghttp3 library
|
||||
|
||||
Result Variables
|
||||
^^^^^^^^^^^^^^^^
|
||||
|
||||
``NGHTTP3_FOUND``
|
||||
System has nghttp3
|
||||
``NGHTTP3_INCLUDE_DIRS``
|
||||
The nghttp3 include directories.
|
||||
``NGHTTP3_LIBRARIES``
|
||||
The libraries needed to use nghttp3
|
||||
``NGHTTP3_VERSION``
|
||||
version of nghttp3.
|
||||
#]=======================================================================]
|
||||
|
||||
if(UNIX)
|
||||
find_package(PkgConfig QUIET)
|
||||
pkg_search_module(PC_NGHTTP3 libnghttp3)
|
||||
endif()
|
||||
|
||||
find_path(NGHTTP3_INCLUDE_DIR nghttp3/nghttp3.h
|
||||
HINTS
|
||||
${PC_NGHTTP3_INCLUDEDIR}
|
||||
${PC_NGHTTP3_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
find_library(NGHTTP3_LIBRARY NAMES nghttp3
|
||||
HINTS
|
||||
${PC_NGHTTP3_LIBDIR}
|
||||
${PC_NGHTTP3_LIBRARY_DIRS}
|
||||
)
|
||||
|
||||
if(PC_NGHTTP3_VERSION)
|
||||
set(NGHTTP3_VERSION ${PC_NGHTTP3_VERSION})
|
||||
endif()
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(NGHTTP3
|
||||
REQUIRED_VARS
|
||||
NGHTTP3_LIBRARY
|
||||
NGHTTP3_INCLUDE_DIR
|
||||
VERSION_VAR NGHTTP3_VERSION
|
||||
)
|
||||
|
||||
if(NGHTTP3_FOUND)
|
||||
set(NGHTTP3_LIBRARIES ${NGHTTP3_LIBRARY})
|
||||
set(NGHTTP3_INCLUDE_DIRS ${NGHTTP3_INCLUDE_DIR})
|
||||
endif()
|
||||
|
||||
mark_as_advanced(NGHTTP3_INCLUDE_DIRS NGHTTP3_LIBRARIES)
|
115
src/dependencies/cmcurl/CMake/FindNGTCP2.cmake
Normal file
115
src/dependencies/cmcurl/CMake/FindNGTCP2.cmake
Normal file
|
@ -0,0 +1,115 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
|
||||
#[=======================================================================[.rst:
|
||||
FindNGTCP2
|
||||
----------
|
||||
|
||||
Find the ngtcp2 library
|
||||
|
||||
This module accepts optional COMPONENTS to control the crypto library (these are
|
||||
mutually exclusive)::
|
||||
|
||||
OpenSSL: Use libngtcp2_crypto_openssl
|
||||
GnuTLS: Use libngtcp2_crypto_gnutls
|
||||
|
||||
Result Variables
|
||||
^^^^^^^^^^^^^^^^
|
||||
|
||||
``NGTCP2_FOUND``
|
||||
System has ngtcp2
|
||||
``NGTCP2_INCLUDE_DIRS``
|
||||
The ngtcp2 include directories.
|
||||
``NGTCP2_LIBRARIES``
|
||||
The libraries needed to use ngtcp2
|
||||
``NGTCP2_VERSION``
|
||||
version of ngtcp2.
|
||||
#]=======================================================================]
|
||||
|
||||
if(UNIX)
|
||||
find_package(PkgConfig QUIET)
|
||||
pkg_search_module(PC_NGTCP2 libngtcp2)
|
||||
endif()
|
||||
|
||||
find_path(NGTCP2_INCLUDE_DIR ngtcp2/ngtcp2.h
|
||||
HINTS
|
||||
${PC_NGTCP2_INCLUDEDIR}
|
||||
${PC_NGTCP2_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
find_library(NGTCP2_LIBRARY NAMES ngtcp2
|
||||
HINTS
|
||||
${PC_NGTCP2_LIBDIR}
|
||||
${PC_NGTCP2_LIBRARY_DIRS}
|
||||
)
|
||||
|
||||
if(PC_NGTCP2_VERSION)
|
||||
set(NGTCP2_VERSION ${PC_NGTCP2_VERSION})
|
||||
endif()
|
||||
|
||||
if(NGTCP2_FIND_COMPONENTS)
|
||||
set(NGTCP2_CRYPTO_BACKEND "")
|
||||
foreach(component IN LISTS NGTCP2_FIND_COMPONENTS)
|
||||
if(component MATCHES "^(BoringSSL|OpenSSL|wolfSSL|GnuTLS)")
|
||||
if(NGTCP2_CRYPTO_BACKEND)
|
||||
message(FATAL_ERROR "NGTCP2: Only one crypto library can be selected")
|
||||
endif()
|
||||
set(NGTCP2_CRYPTO_BACKEND ${component})
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
if(NGTCP2_CRYPTO_BACKEND)
|
||||
string(TOLOWER "ngtcp2_crypto_${NGTCP2_CRYPTO_BACKEND}" _crypto_library)
|
||||
if(UNIX)
|
||||
pkg_search_module(PC_${_crypto_library} lib${_crypto_library})
|
||||
endif()
|
||||
find_library(${_crypto_library}_LIBRARY
|
||||
NAMES
|
||||
${_crypto_library}
|
||||
HINTS
|
||||
${PC_${_crypto_library}_LIBDIR}
|
||||
${PC_${_crypto_library}_LIBRARY_DIRS}
|
||||
)
|
||||
if(${_crypto_library}_LIBRARY)
|
||||
set(NGTCP2_${NGTCP2_CRYPTO_BACKEND}_FOUND TRUE)
|
||||
set(NGTCP2_CRYPTO_LIBRARY ${${_crypto_library}_LIBRARY})
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(NGTCP2
|
||||
REQUIRED_VARS
|
||||
NGTCP2_LIBRARY
|
||||
NGTCP2_INCLUDE_DIR
|
||||
VERSION_VAR NGTCP2_VERSION
|
||||
HANDLE_COMPONENTS
|
||||
)
|
||||
|
||||
if(NGTCP2_FOUND)
|
||||
set(NGTCP2_LIBRARIES ${NGTCP2_LIBRARY} ${NGTCP2_CRYPTO_LIBRARY})
|
||||
set(NGTCP2_INCLUDE_DIRS ${NGTCP2_INCLUDE_DIR})
|
||||
endif()
|
||||
|
||||
mark_as_advanced(NGTCP2_INCLUDE_DIRS NGTCP2_LIBRARIES)
|
40
src/dependencies/cmcurl/CMake/FindNSS.cmake
Normal file
40
src/dependencies/cmcurl/CMake/FindNSS.cmake
Normal file
|
@ -0,0 +1,40 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
if(UNIX)
|
||||
find_package(PkgConfig QUIET)
|
||||
pkg_search_module(PC_NSS nss)
|
||||
endif()
|
||||
if(NOT PC_NSS_FOUND)
|
||||
return()
|
||||
endif()
|
||||
|
||||
set(NSS_LIBRARIES ${PC_NSS_LINK_LIBRARIES})
|
||||
set(NSS_INCLUDE_DIRS ${PC_NSS_INCLUDE_DIRS})
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(NSS
|
||||
REQUIRED_VARS NSS_LIBRARIES NSS_INCLUDE_DIRS
|
||||
VERSION_VAR PC_NSS_VERSION)
|
||||
|
||||
mark_as_advanced(NSS_INCLUDE_DIRS NSS_LIBRARIES)
|
70
src/dependencies/cmcurl/CMake/FindQUICHE.cmake
Normal file
70
src/dependencies/cmcurl/CMake/FindQUICHE.cmake
Normal file
|
@ -0,0 +1,70 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
|
||||
#[=======================================================================[.rst:
|
||||
FindQUICHE
|
||||
----------
|
||||
|
||||
Find the quiche library
|
||||
|
||||
Result Variables
|
||||
^^^^^^^^^^^^^^^^
|
||||
|
||||
``QUICHE_FOUND``
|
||||
System has quiche
|
||||
``QUICHE_INCLUDE_DIRS``
|
||||
The quiche include directories.
|
||||
``QUICHE_LIBRARIES``
|
||||
The libraries needed to use quiche
|
||||
#]=======================================================================]
|
||||
if(UNIX)
|
||||
find_package(PkgConfig QUIET)
|
||||
pkg_search_module(PC_QUICHE quiche)
|
||||
endif()
|
||||
|
||||
find_path(QUICHE_INCLUDE_DIR quiche.h
|
||||
HINTS
|
||||
${PC_QUICHE_INCLUDEDIR}
|
||||
${PC_QUICHE_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
find_library(QUICHE_LIBRARY NAMES quiche
|
||||
HINTS
|
||||
${PC_QUICHE_LIBDIR}
|
||||
${PC_QUICHE_LIBRARY_DIRS}
|
||||
)
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(QUICHE
|
||||
REQUIRED_VARS
|
||||
QUICHE_LIBRARY
|
||||
QUICHE_INCLUDE_DIR
|
||||
)
|
||||
|
||||
if(QUICHE_FOUND)
|
||||
set(QUICHE_LIBRARIES ${QUICHE_LIBRARY})
|
||||
set(QUICHE_INCLUDE_DIRS ${QUICHE_INCLUDE_DIR})
|
||||
endif()
|
||||
|
||||
mark_as_advanced(QUICHE_INCLUDE_DIRS QUICHE_LIBRARIES)
|
36
src/dependencies/cmcurl/CMake/FindWolfSSL.cmake
Normal file
36
src/dependencies/cmcurl/CMake/FindWolfSSL.cmake
Normal file
|
@ -0,0 +1,36 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
find_path(WolfSSL_INCLUDE_DIR NAMES wolfssl/ssl.h)
|
||||
find_library(WolfSSL_LIBRARY NAMES wolfssl)
|
||||
mark_as_advanced(WolfSSL_INCLUDE_DIR WolfSSL_LIBRARY)
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(WolfSSL
|
||||
REQUIRED_VARS WolfSSL_INCLUDE_DIR WolfSSL_LIBRARY
|
||||
)
|
||||
|
||||
if(WolfSSL_FOUND)
|
||||
set(WolfSSL_INCLUDE_DIRS ${WolfSSL_INCLUDE_DIR})
|
||||
set(WolfSSL_LIBRARIES ${WolfSSL_LIBRARY})
|
||||
endif()
|
71
src/dependencies/cmcurl/CMake/FindZstd.cmake
Normal file
71
src/dependencies/cmcurl/CMake/FindZstd.cmake
Normal file
|
@ -0,0 +1,71 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
|
||||
#[=======================================================================[.rst:
|
||||
FindZstd
|
||||
----------
|
||||
|
||||
Find the zstd library
|
||||
|
||||
Result Variables
|
||||
^^^^^^^^^^^^^^^^
|
||||
|
||||
``Zstd_FOUND``
|
||||
System has zstd
|
||||
``Zstd_INCLUDE_DIRS``
|
||||
The zstd include directories.
|
||||
``Zstd_LIBRARIES``
|
||||
The libraries needed to use zstd
|
||||
#]=======================================================================]
|
||||
|
||||
if(UNIX)
|
||||
find_package(PkgConfig QUIET)
|
||||
pkg_search_module(PC_Zstd libzstd)
|
||||
endif()
|
||||
|
||||
find_path(Zstd_INCLUDE_DIR zstd.h
|
||||
HINTS
|
||||
${PC_Zstd_INCLUDEDIR}
|
||||
${PC_Zstd_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
find_library(Zstd_LIBRARY NAMES zstd
|
||||
HINTS
|
||||
${PC_Zstd_LIBDIR}
|
||||
${PC_Zstd_LIBRARY_DIRS}
|
||||
)
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(Zstd
|
||||
REQUIRED_VARS
|
||||
Zstd_LIBRARY
|
||||
Zstd_INCLUDE_DIR
|
||||
)
|
||||
|
||||
if(Zstd_FOUND)
|
||||
set(Zstd_LIBRARIES ${Zstd_LIBRARY})
|
||||
set(Zstd_INCLUDE_DIRS ${Zstd_INCLUDE_DIR})
|
||||
endif()
|
||||
|
||||
mark_as_advanced(Zstd_INCLUDE_DIRS Zstd_LIBRARIES)
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
#File defines convenience macros for available feature testing
|
||||
|
||||
# This macro checks if the symbol exists in the library and if it
|
||||
|
@ -86,3 +109,14 @@ macro(curl_nroff_check)
|
|||
message(WARNING "Found no *nroff program")
|
||||
endif()
|
||||
endmacro()
|
||||
|
||||
macro(optional_dependency DEPENDENCY)
|
||||
set(CURL_${DEPENDENCY} AUTO CACHE STRING "Build curl with ${DEPENDENCY} support (AUTO, ON or OFF)")
|
||||
set_property(CACHE CURL_${DEPENDENCY} PROPERTY STRINGS AUTO ON OFF)
|
||||
|
||||
if(CURL_${DEPENDENCY} STREQUAL AUTO)
|
||||
find_package(${DEPENDENCY})
|
||||
elseif(CURL_${DEPENDENCY})
|
||||
find_package(${DEPENDENCY} REQUIRED)
|
||||
endif()
|
||||
endmacro()
|
||||
|
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
include(CheckCSourceCompiles)
|
||||
# The begin of the sources (macros and includes)
|
||||
set(_source_epilogue "#undef inline")
|
||||
|
@ -12,7 +35,6 @@ set(signature_call_conv)
|
|||
if(HAVE_WINDOWS_H)
|
||||
add_header_include(HAVE_WINSOCK2_H "winsock2.h")
|
||||
add_header_include(HAVE_WINDOWS_H "windows.h")
|
||||
add_header_include(HAVE_WINSOCK_H "winsock.h")
|
||||
set(_source_epilogue
|
||||
"${_source_epilogue}\n#ifndef WIN32_LEAN_AND_MEAN\n#define WIN32_LEAN_AND_MEAN\n#endif")
|
||||
set(signature_call_conv "PASCAL")
|
||||
|
@ -26,138 +48,6 @@ endif()
|
|||
|
||||
set(CMAKE_TRY_COMPILE_TARGET_TYPE STATIC_LIBRARY)
|
||||
|
||||
check_c_source_compiles("${_source_epilogue}
|
||||
int main(void) {
|
||||
recv(0, 0, 0, 0);
|
||||
return 0;
|
||||
}" curl_cv_recv)
|
||||
if(curl_cv_recv)
|
||||
if(NOT DEFINED curl_cv_func_recv_args OR "${curl_cv_func_recv_args}" STREQUAL "unknown")
|
||||
foreach(recv_retv "int" "ssize_t" )
|
||||
foreach(recv_arg1 "SOCKET" "int" )
|
||||
foreach(recv_arg2 "char *" "void *" )
|
||||
foreach(recv_arg3 "int" "size_t" "socklen_t" "unsigned int")
|
||||
foreach(recv_arg4 "int" "unsigned int")
|
||||
if(NOT curl_cv_func_recv_done)
|
||||
unset(curl_cv_func_recv_test CACHE)
|
||||
check_c_source_compiles("
|
||||
${_source_epilogue}
|
||||
extern ${recv_retv} ${signature_call_conv}
|
||||
recv(${recv_arg1}, ${recv_arg2}, ${recv_arg3}, ${recv_arg4});
|
||||
int main(void) {
|
||||
${recv_arg1} s=0;
|
||||
${recv_arg2} buf=0;
|
||||
${recv_arg3} len=0;
|
||||
${recv_arg4} flags=0;
|
||||
${recv_retv} res = recv(s, buf, len, flags);
|
||||
(void) res;
|
||||
return 0;
|
||||
}"
|
||||
curl_cv_func_recv_test)
|
||||
message(STATUS
|
||||
"Tested: ${recv_retv} recv(${recv_arg1}, ${recv_arg2}, ${recv_arg3}, ${recv_arg4})")
|
||||
if(curl_cv_func_recv_test)
|
||||
set(curl_cv_func_recv_args
|
||||
"${recv_arg1},${recv_arg2},${recv_arg3},${recv_arg4},${recv_retv}")
|
||||
set(RECV_TYPE_ARG1 "${recv_arg1}")
|
||||
set(RECV_TYPE_ARG2 "${recv_arg2}")
|
||||
set(RECV_TYPE_ARG3 "${recv_arg3}")
|
||||
set(RECV_TYPE_ARG4 "${recv_arg4}")
|
||||
set(RECV_TYPE_RETV "${recv_retv}")
|
||||
set(HAVE_RECV 1)
|
||||
set(curl_cv_func_recv_done 1)
|
||||
endif()
|
||||
endif()
|
||||
endforeach()
|
||||
endforeach()
|
||||
endforeach()
|
||||
endforeach()
|
||||
endforeach()
|
||||
else()
|
||||
string(REGEX REPLACE "^([^,]*),[^,]*,[^,]*,[^,]*,[^,]*$" "\\1" RECV_TYPE_ARG1 "${curl_cv_func_recv_args}")
|
||||
string(REGEX REPLACE "^[^,]*,([^,]*),[^,]*,[^,]*,[^,]*$" "\\1" RECV_TYPE_ARG2 "${curl_cv_func_recv_args}")
|
||||
string(REGEX REPLACE "^[^,]*,[^,]*,([^,]*),[^,]*,[^,]*$" "\\1" RECV_TYPE_ARG3 "${curl_cv_func_recv_args}")
|
||||
string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,([^,]*),[^,]*$" "\\1" RECV_TYPE_ARG4 "${curl_cv_func_recv_args}")
|
||||
string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,[^,]*,([^,]*)$" "\\1" RECV_TYPE_RETV "${curl_cv_func_recv_args}")
|
||||
endif()
|
||||
|
||||
if("${curl_cv_func_recv_args}" STREQUAL "unknown")
|
||||
message(FATAL_ERROR "Cannot find proper types to use for recv args")
|
||||
endif()
|
||||
else()
|
||||
message(FATAL_ERROR "Unable to link function recv")
|
||||
endif()
|
||||
set(curl_cv_func_recv_args "${curl_cv_func_recv_args}" CACHE INTERNAL "Arguments for recv")
|
||||
set(HAVE_RECV 1)
|
||||
|
||||
check_c_source_compiles("${_source_epilogue}
|
||||
int main(void) {
|
||||
send(0, 0, 0, 0);
|
||||
return 0;
|
||||
}" curl_cv_send)
|
||||
if(curl_cv_send)
|
||||
if(NOT DEFINED curl_cv_func_send_args OR "${curl_cv_func_send_args}" STREQUAL "unknown")
|
||||
foreach(send_retv "int" "ssize_t" )
|
||||
foreach(send_arg1 "SOCKET" "int" "ssize_t" )
|
||||
foreach(send_arg2 "const char *" "const void *" "void *" "char *")
|
||||
foreach(send_arg3 "int" "size_t" "socklen_t" "unsigned int")
|
||||
foreach(send_arg4 "int" "unsigned int")
|
||||
if(NOT curl_cv_func_send_done)
|
||||
unset(curl_cv_func_send_test CACHE)
|
||||
check_c_source_compiles("
|
||||
${_source_epilogue}
|
||||
extern ${send_retv} ${signature_call_conv}
|
||||
send(${send_arg1}, ${send_arg2}, ${send_arg3}, ${send_arg4});
|
||||
int main(void) {
|
||||
${send_arg1} s=0;
|
||||
${send_arg2} buf=0;
|
||||
${send_arg3} len=0;
|
||||
${send_arg4} flags=0;
|
||||
${send_retv} res = send(s, buf, len, flags);
|
||||
(void) res;
|
||||
return 0;
|
||||
}"
|
||||
curl_cv_func_send_test)
|
||||
message(STATUS
|
||||
"Tested: ${send_retv} send(${send_arg1}, ${send_arg2}, ${send_arg3}, ${send_arg4})")
|
||||
if(curl_cv_func_send_test)
|
||||
string(REGEX REPLACE "(const) .*" "\\1" send_qual_arg2 "${send_arg2}")
|
||||
string(REGEX REPLACE "const (.*)" "\\1" send_arg2 "${send_arg2}")
|
||||
set(curl_cv_func_send_args
|
||||
"${send_arg1},${send_arg2},${send_arg3},${send_arg4},${send_retv},${send_qual_arg2}")
|
||||
set(SEND_TYPE_ARG1 "${send_arg1}")
|
||||
set(SEND_TYPE_ARG2 "${send_arg2}")
|
||||
set(SEND_TYPE_ARG3 "${send_arg3}")
|
||||
set(SEND_TYPE_ARG4 "${send_arg4}")
|
||||
set(SEND_TYPE_RETV "${send_retv}")
|
||||
set(HAVE_SEND 1)
|
||||
set(curl_cv_func_send_done 1)
|
||||
endif()
|
||||
endif()
|
||||
endforeach()
|
||||
endforeach()
|
||||
endforeach()
|
||||
endforeach()
|
||||
endforeach()
|
||||
else()
|
||||
string(REGEX REPLACE "^([^,]*),[^,]*,[^,]*,[^,]*,[^,]*,[^,]*$" "\\1" SEND_TYPE_ARG1 "${curl_cv_func_send_args}")
|
||||
string(REGEX REPLACE "^[^,]*,([^,]*),[^,]*,[^,]*,[^,]*,[^,]*$" "\\1" SEND_TYPE_ARG2 "${curl_cv_func_send_args}")
|
||||
string(REGEX REPLACE "^[^,]*,[^,]*,([^,]*),[^,]*,[^,]*,[^,]*$" "\\1" SEND_TYPE_ARG3 "${curl_cv_func_send_args}")
|
||||
string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,([^,]*),[^,]*,[^,]*$" "\\1" SEND_TYPE_ARG4 "${curl_cv_func_send_args}")
|
||||
string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,[^,]*,([^,]*),[^,]*$" "\\1" SEND_TYPE_RETV "${curl_cv_func_send_args}")
|
||||
string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,[^,]*,[^,]*,([^,]*)$" "\\1" SEND_QUAL_ARG2 "${curl_cv_func_send_args}")
|
||||
endif()
|
||||
|
||||
if("${curl_cv_func_send_args}" STREQUAL "unknown")
|
||||
message(FATAL_ERROR "Cannot find proper types to use for send args")
|
||||
endif()
|
||||
set(SEND_QUAL_ARG2 "const")
|
||||
else()
|
||||
message(FATAL_ERROR "Unable to link function send")
|
||||
endif()
|
||||
set(curl_cv_func_send_args "${curl_cv_func_send_args}" CACHE INTERNAL "Arguments for send")
|
||||
set(HAVE_SEND 1)
|
||||
|
||||
check_c_source_compiles("${_source_epilogue}
|
||||
int main(void) {
|
||||
int flag = MSG_NOSIGNAL;
|
||||
|
@ -179,28 +69,6 @@ int main(void) {
|
|||
return 0;
|
||||
}" HAVE_STRUCT_TIMEVAL)
|
||||
|
||||
set(HAVE_SIG_ATOMIC_T 1)
|
||||
set(CMAKE_REQUIRED_FLAGS)
|
||||
if(HAVE_SIGNAL_H)
|
||||
set(CMAKE_REQUIRED_FLAGS "-DHAVE_SIGNAL_H")
|
||||
set(CMAKE_EXTRA_INCLUDE_FILES "signal.h")
|
||||
endif()
|
||||
check_type_size("sig_atomic_t" SIZEOF_SIG_ATOMIC_T)
|
||||
if(HAVE_SIZEOF_SIG_ATOMIC_T)
|
||||
check_c_source_compiles("
|
||||
#ifdef HAVE_SIGNAL_H
|
||||
# include <signal.h>
|
||||
#endif
|
||||
int main(void) {
|
||||
static volatile sig_atomic_t dummy = 0;
|
||||
(void)dummy;
|
||||
return 0;
|
||||
}" HAVE_SIG_ATOMIC_T_NOT_VOLATILE)
|
||||
if(NOT HAVE_SIG_ATOMIC_T_NOT_VOLATILE)
|
||||
set(HAVE_SIG_ATOMIC_T_VOLATILE 1)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(HAVE_WINDOWS_H)
|
||||
set(CMAKE_EXTRA_INCLUDE_FILES winsock2.h)
|
||||
else()
|
||||
|
@ -217,48 +85,52 @@ endif()
|
|||
|
||||
unset(CMAKE_TRY_COMPILE_TARGET_TYPE)
|
||||
|
||||
if(NOT DEFINED CMAKE_TOOLCHAIN_FILE)
|
||||
# if not cross-compilation...
|
||||
include(CheckCSourceRuns)
|
||||
set(CMAKE_REQUIRED_FLAGS "")
|
||||
if(HAVE_SYS_POLL_H)
|
||||
set(CMAKE_REQUIRED_FLAGS "-DHAVE_SYS_POLL_H")
|
||||
elseif(HAVE_POLL_H)
|
||||
set(CMAKE_REQUIRED_FLAGS "-DHAVE_POLL_H")
|
||||
endif()
|
||||
check_c_source_runs("
|
||||
#include <stdlib.h>
|
||||
#include <sys/time.h>
|
||||
if(NOT CMAKE_CROSSCOMPILING)
|
||||
if(NOT ${CMAKE_SYSTEM_NAME} MATCHES "Darwin" AND NOT ${CMAKE_SYSTEM_NAME} MATCHES "iOS")
|
||||
# only try this on non-apple platforms
|
||||
|
||||
#ifdef HAVE_SYS_POLL_H
|
||||
# include <sys/poll.h>
|
||||
#elif HAVE_POLL_H
|
||||
# include <poll.h>
|
||||
#endif
|
||||
# if not cross-compilation...
|
||||
include(CheckCSourceRuns)
|
||||
set(CMAKE_REQUIRED_FLAGS "")
|
||||
if(HAVE_SYS_POLL_H)
|
||||
set(CMAKE_REQUIRED_FLAGS "-DHAVE_SYS_POLL_H")
|
||||
elseif(HAVE_POLL_H)
|
||||
set(CMAKE_REQUIRED_FLAGS "-DHAVE_POLL_H")
|
||||
endif()
|
||||
check_c_source_runs("
|
||||
#include <stdlib.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
int main(void)
|
||||
{
|
||||
if(0 != poll(0, 0, 10)) {
|
||||
return 1; /* fail */
|
||||
}
|
||||
else {
|
||||
/* detect the 10.12 poll() breakage */
|
||||
struct timeval before, after;
|
||||
int rc;
|
||||
size_t us;
|
||||
#ifdef HAVE_SYS_POLL_H
|
||||
# include <sys/poll.h>
|
||||
#elif HAVE_POLL_H
|
||||
# include <poll.h>
|
||||
#endif
|
||||
|
||||
gettimeofday(&before, NULL);
|
||||
rc = poll(NULL, 0, 500);
|
||||
gettimeofday(&after, NULL);
|
||||
|
||||
us = (after.tv_sec - before.tv_sec) * 1000000 +
|
||||
(after.tv_usec - before.tv_usec);
|
||||
|
||||
if(us < 400000) {
|
||||
return 1;
|
||||
int main(void)
|
||||
{
|
||||
if(0 != poll(0, 0, 10)) {
|
||||
return 1; /* fail */
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
else {
|
||||
/* detect the 10.12 poll() breakage */
|
||||
struct timeval before, after;
|
||||
int rc;
|
||||
size_t us;
|
||||
|
||||
gettimeofday(&before, NULL);
|
||||
rc = poll(NULL, 0, 500);
|
||||
gettimeofday(&after, NULL);
|
||||
|
||||
us = (after.tv_sec - before.tv_sec) * 1000000 +
|
||||
(after.tv_usec - before.tv_usec);
|
||||
|
||||
if(us < 400000) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}" HAVE_POLL_FINE)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
|
|
|
@ -1,35 +1,41 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
if(NOT UNIX)
|
||||
if(WIN32)
|
||||
set(HAVE_LIBDL 0)
|
||||
set(HAVE_LIBUCB 0)
|
||||
set(HAVE_LIBSOCKET 0)
|
||||
set(NOT_NEED_LIBNSL 0)
|
||||
set(HAVE_LIBNSL 0)
|
||||
set(HAVE_GETHOSTNAME 1)
|
||||
set(HAVE_LIBZ 0)
|
||||
set(HAVE_LIBCRYPTO 0)
|
||||
|
||||
set(HAVE_DLOPEN 0)
|
||||
|
||||
set(HAVE_ALLOCA_H 0)
|
||||
set(HAVE_ARPA_INET_H 0)
|
||||
set(HAVE_DLFCN_H 0)
|
||||
set(HAVE_FCNTL_H 1)
|
||||
set(HAVE_INTTYPES_H 0)
|
||||
set(HAVE_IO_H 1)
|
||||
set(HAVE_MALLOC_H 1)
|
||||
set(HAVE_MEMORY_H 1)
|
||||
set(HAVE_NETDB_H 0)
|
||||
set(HAVE_NETINET_IF_ETHER_H 0)
|
||||
set(HAVE_NETINET_IN_H 0)
|
||||
set(HAVE_NET_IF_H 0)
|
||||
set(HAVE_PROCESS_H 1)
|
||||
set(HAVE_PWD_H 0)
|
||||
set(HAVE_SETJMP_H 1)
|
||||
set(HAVE_SGTTY_H 0)
|
||||
set(HAVE_SIGNAL_H 1)
|
||||
set(HAVE_SOCKIO_H 0)
|
||||
set(HAVE_STDINT_H 0)
|
||||
set(HAVE_STDLIB_H 1)
|
||||
set(HAVE_STRINGS_H 0)
|
||||
set(HAVE_STRING_H 1)
|
||||
|
@ -45,54 +51,26 @@ if(NOT UNIX)
|
|||
set(HAVE_TERMIOS_H 0)
|
||||
set(HAVE_TERMIO_H 0)
|
||||
set(HAVE_TIME_H 1)
|
||||
set(HAVE_UNISTD_H 0)
|
||||
set(HAVE_UTIME_H 0)
|
||||
set(HAVE_X509_H 0)
|
||||
set(HAVE_ZLIB_H 0)
|
||||
|
||||
set(HAVE_SOCKET 1)
|
||||
set(HAVE_POLL 0)
|
||||
set(HAVE_SELECT 1)
|
||||
set(HAVE_STRDUP 1)
|
||||
set(HAVE_STRSTR 1)
|
||||
set(HAVE_STRTOK_R 0)
|
||||
set(HAVE_STRFTIME 1)
|
||||
set(HAVE_UNAME 0)
|
||||
set(HAVE_STRCASECMP 0)
|
||||
set(HAVE_STRICMP 1)
|
||||
set(HAVE_STRCMPI 1)
|
||||
set(HAVE_GETHOSTBYADDR 1)
|
||||
set(HAVE_GETTIMEOFDAY 0)
|
||||
set(HAVE_INET_ADDR 1)
|
||||
set(HAVE_INET_NTOA 1)
|
||||
set(HAVE_INET_NTOA_R 0)
|
||||
set(HAVE_TCGETATTR 0)
|
||||
set(HAVE_TCSETATTR 0)
|
||||
set(HAVE_PERROR 1)
|
||||
set(HAVE_CLOSESOCKET 1)
|
||||
set(HAVE_SETVBUF 0)
|
||||
set(HAVE_SIGSETJMP 0)
|
||||
set(HAVE_SOCKADDR_IN6_SIN6_SCOPE_ID 1)
|
||||
set(HAVE_GETPASS_R 0)
|
||||
set(HAVE_STRLCAT 0)
|
||||
set(HAVE_GETPWUID 0)
|
||||
set(HAVE_GETEUID 0)
|
||||
set(HAVE_UTIME 1)
|
||||
set(HAVE_RAND_EGD 0)
|
||||
set(HAVE_RAND_SCREEN 0)
|
||||
set(HAVE_RAND_STATUS 0)
|
||||
set(HAVE_GMTIME_R 0)
|
||||
set(HAVE_LOCALTIME_R 0)
|
||||
set(HAVE_GETHOSTBYADDR_R 0)
|
||||
set(HAVE_GETHOSTBYNAME_R 0)
|
||||
set(HAVE_SIGNAL_FUNC 1)
|
||||
set(HAVE_SIGNAL_MACRO 0)
|
||||
set(HAVE_SIGNAL 1)
|
||||
|
||||
set(HAVE_GETHOSTBYADDR_R_5 0)
|
||||
set(HAVE_GETHOSTBYADDR_R_5_REENTRANT 0)
|
||||
set(HAVE_GETHOSTBYADDR_R_7 0)
|
||||
set(HAVE_GETHOSTBYADDR_R_7_REENTRANT 0)
|
||||
set(HAVE_GETHOSTBYADDR_R_8 0)
|
||||
set(HAVE_GETHOSTBYADDR_R_8_REENTRANT 0)
|
||||
set(HAVE_GETHOSTBYNAME_R_3 0)
|
||||
set(HAVE_GETHOSTBYNAME_R_3_REENTRANT 0)
|
||||
set(HAVE_GETHOSTBYNAME_R_5 0)
|
||||
|
@ -103,15 +81,7 @@ if(NOT UNIX)
|
|||
set(TIME_WITH_SYS_TIME 0)
|
||||
set(HAVE_O_NONBLOCK 0)
|
||||
set(HAVE_IN_ADDR_T 0)
|
||||
set(HAVE_INET_NTOA_R_DECL 0)
|
||||
set(HAVE_INET_NTOA_R_DECL_REENTRANT 0)
|
||||
if(ENABLE_IPV6)
|
||||
set(HAVE_GETADDRINFO 1)
|
||||
else()
|
||||
set(HAVE_GETADDRINFO 0)
|
||||
endif()
|
||||
set(STDC_HEADERS 1)
|
||||
set(RETSIGTYPE_TEST 1)
|
||||
|
||||
set(HAVE_SIGACTION 0)
|
||||
set(HAVE_MACRO_SIGSETJMP 0)
|
||||
|
|
|
@ -1,13 +1,35 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
# File containing various utilities
|
||||
|
||||
# Returns a list of arguments that evaluate to true
|
||||
function(count_true output_count_var)
|
||||
set(lst)
|
||||
set(lst_len 0)
|
||||
foreach(option_var IN LISTS ARGN)
|
||||
if(${option_var})
|
||||
list(APPEND lst ${option_var})
|
||||
math(EXPR lst_len "${lst_len} + 1")
|
||||
endif()
|
||||
endforeach()
|
||||
list(LENGTH lst lst_len)
|
||||
set(${output_count_var} ${lst_len} PARENT_SCOPE)
|
||||
endfunction()
|
||||
|
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
if(NOT EXISTS "@CMAKE_CURRENT_BINARY_DIR@/install_manifest.txt")
|
||||
message(FATAL_ERROR "Cannot find install manifest: @CMAKE_CURRENT_BINARY_DIR@/install_manifest.txt")
|
||||
endif()
|
||||
|
|
|
@ -1,3 +1,26 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
@PACKAGE_INIT@
|
||||
|
||||
include(CMakeFindDependencyMacro)
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,6 +1,6 @@
|
|||
COPYRIGHT AND PERMISSION NOTICE
|
||||
|
||||
Copyright (c) 1996 - 2019, Daniel Stenberg, <daniel@haxx.se>, and many
|
||||
Copyright (c) 1996 - 2023, Daniel Stenberg, <daniel@haxx.se>, and many
|
||||
contributors, see the THANKS file.
|
||||
|
||||
All rights reserved.
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,5 +1,5 @@
|
|||
#ifndef __CURL_CURLVER_H
|
||||
#define __CURL_CURLVER_H
|
||||
#ifndef CURLINC_CURLVER_H
|
||||
#define CURLINC_CURLVER_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,26 +20,28 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/* This header file contains nothing but libcurl version info, generated by
|
||||
a script at release-time. This was made its own header file in 7.11.2 */
|
||||
|
||||
/* This is the global package copyright */
|
||||
#define LIBCURL_COPYRIGHT "1996 - 2019 Daniel Stenberg, <daniel@haxx.se>."
|
||||
#define LIBCURL_COPYRIGHT "Daniel Stenberg, <daniel@haxx.se>."
|
||||
|
||||
/* This is the version number of the libcurl package from which this header
|
||||
file origins: */
|
||||
#define LIBCURL_VERSION "7.65.0"
|
||||
#define LIBCURL_VERSION "8.0.1"
|
||||
|
||||
/* The numeric version number is also available "in parts" by using these
|
||||
defines: */
|
||||
#define LIBCURL_VERSION_MAJOR 7
|
||||
#define LIBCURL_VERSION_MINOR 65
|
||||
#define LIBCURL_VERSION_PATCH 0
|
||||
#define LIBCURL_VERSION_MAJOR 8
|
||||
#define LIBCURL_VERSION_MINOR 0
|
||||
#define LIBCURL_VERSION_PATCH 1
|
||||
|
||||
/* This is the numeric version of the libcurl version number, meant for easier
|
||||
parsing and comparions by programs. The LIBCURL_VERSION_NUM define will
|
||||
parsing and comparisons by programs. The LIBCURL_VERSION_NUM define will
|
||||
always follow this syntax:
|
||||
|
||||
0xXXYYZZ
|
||||
|
@ -57,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 0x074100
|
||||
#define LIBCURL_VERSION_NUM 0x080001
|
||||
|
||||
/*
|
||||
* This is the date and time when the full source package was created. The
|
||||
|
@ -74,4 +76,4 @@
|
|||
#define CURL_AT_LEAST_VERSION(x,y,z) \
|
||||
(LIBCURL_VERSION_NUM >= CURL_VERSION_BITS(x, y, z))
|
||||
|
||||
#endif /* __CURL_CURLVER_H */
|
||||
#endif /* CURLINC_CURLVER_H */
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
#ifndef __CURL_EASY_H
|
||||
#define __CURL_EASY_H
|
||||
#ifndef CURLINC_EASY_H
|
||||
#define CURLINC_EASY_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2016, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,11 +20,24 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/* Flag bits in the curl_blob struct: */
|
||||
#define CURL_BLOB_COPY 1 /* tell libcurl to copy the data */
|
||||
#define CURL_BLOB_NOCOPY 0 /* tell libcurl to NOT copy the data */
|
||||
|
||||
struct curl_blob {
|
||||
void *data;
|
||||
size_t len;
|
||||
unsigned int flags; /* bit 0 is defined, the rest are reserved and should be
|
||||
left zeroes */
|
||||
};
|
||||
|
||||
CURL_EXTERN CURL *curl_easy_init(void);
|
||||
CURL_EXTERN CURLcode curl_easy_setopt(CURL *curl, CURLoption option, ...);
|
||||
CURL_EXTERN CURLcode curl_easy_perform(CURL *curl);
|
||||
|
@ -106,7 +119,7 @@ CURL_EXTERN CURLcode curl_easy_send(CURL *curl, const void *buffer,
|
|||
CURL_EXTERN CURLcode curl_easy_upkeep(CURL *curl);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
} /* end of extern "C" */
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
|
74
src/dependencies/cmcurl/include/curl/header.h
Normal file
74
src/dependencies/cmcurl/include/curl/header.h
Normal file
|
@ -0,0 +1,74 @@
|
|||
#ifndef CURLINC_HEADER_H
|
||||
#define CURLINC_HEADER_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct curl_header {
|
||||
char *name; /* this might not use the same case */
|
||||
char *value;
|
||||
size_t amount; /* number of headers using this name */
|
||||
size_t index; /* ... of this instance, 0 or higher */
|
||||
unsigned int origin; /* see bits below */
|
||||
void *anchor; /* handle privately used by libcurl */
|
||||
};
|
||||
|
||||
/* 'origin' bits */
|
||||
#define CURLH_HEADER (1<<0) /* plain server header */
|
||||
#define CURLH_TRAILER (1<<1) /* trailers */
|
||||
#define CURLH_CONNECT (1<<2) /* CONNECT headers */
|
||||
#define CURLH_1XX (1<<3) /* 1xx headers */
|
||||
#define CURLH_PSEUDO (1<<4) /* pseudo headers */
|
||||
|
||||
typedef enum {
|
||||
CURLHE_OK,
|
||||
CURLHE_BADINDEX, /* header exists but not with this index */
|
||||
CURLHE_MISSING, /* no such header exists */
|
||||
CURLHE_NOHEADERS, /* no headers at all exist (yet) */
|
||||
CURLHE_NOREQUEST, /* no request with this number was used */
|
||||
CURLHE_OUT_OF_MEMORY, /* out of memory while processing */
|
||||
CURLHE_BAD_ARGUMENT, /* a function argument was not okay */
|
||||
CURLHE_NOT_BUILT_IN /* if API was disabled in the build */
|
||||
} CURLHcode;
|
||||
|
||||
CURL_EXTERN CURLHcode curl_easy_header(CURL *easy,
|
||||
const char *name,
|
||||
size_t index,
|
||||
unsigned int origin,
|
||||
int request,
|
||||
struct curl_header **hout);
|
||||
|
||||
CURL_EXTERN struct curl_header *curl_easy_nextheader(CURL *easy,
|
||||
unsigned int origin,
|
||||
int request,
|
||||
struct curl_header *prev);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} /* end of extern "C" */
|
||||
#endif
|
||||
|
||||
#endif /* CURLINC_HEADER_H */
|
|
@ -1,5 +1,5 @@
|
|||
#ifndef __CURL_MPRINTF_H
|
||||
#define __CURL_MPRINTF_H
|
||||
#ifndef CURLINC_MPRINTF_H
|
||||
#define CURLINC_MPRINTF_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2016, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include <stdarg.h>
|
||||
|
@ -44,7 +46,7 @@ CURL_EXTERN char *curl_maprintf(const char *format, ...);
|
|||
CURL_EXTERN char *curl_mvaprintf(const char *format, va_list args);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
} /* end of extern "C" */
|
||||
#endif
|
||||
|
||||
#endif /* __CURL_MPRINTF_H */
|
||||
#endif /* CURLINC_MPRINTF_H */
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
#ifndef __CURL_MULTI_H
|
||||
#define __CURL_MULTI_H
|
||||
#ifndef CURLINC_MULTI_H
|
||||
#define CURLINC_MULTI_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2017, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
/*
|
||||
This is an "external" header file. Don't give away any internals here!
|
||||
|
@ -72,6 +74,10 @@ typedef enum {
|
|||
attempted to get added - again */
|
||||
CURLM_RECURSIVE_API_CALL, /* an api function was called from inside a
|
||||
callback */
|
||||
CURLM_WAKEUP_FAILURE, /* wakeup is unavailable or failed */
|
||||
CURLM_BAD_FUNCTION_ARGUMENT, /* function called with a bad parameter */
|
||||
CURLM_ABORTED_BY_CALLBACK,
|
||||
CURLM_UNRECOVERABLE_POLL,
|
||||
CURLM_LAST
|
||||
} CURLMcode;
|
||||
|
||||
|
@ -118,7 +124,7 @@ struct curl_waitfd {
|
|||
/*
|
||||
* Name: curl_multi_init()
|
||||
*
|
||||
* Desc: inititalize multi-style curl usage
|
||||
* Desc: initialize multi-style curl usage
|
||||
*
|
||||
* Returns: a new CURLM handle to use in all 'curl_multi' functions.
|
||||
*/
|
||||
|
@ -173,6 +179,29 @@ CURL_EXTERN CURLMcode curl_multi_wait(CURLM *multi_handle,
|
|||
int timeout_ms,
|
||||
int *ret);
|
||||
|
||||
/*
|
||||
* Name: curl_multi_poll()
|
||||
*
|
||||
* Desc: Poll on all fds within a CURLM set as well as any
|
||||
* additional fds passed to the function.
|
||||
*
|
||||
* Returns: CURLMcode type, general multi error code.
|
||||
*/
|
||||
CURL_EXTERN CURLMcode curl_multi_poll(CURLM *multi_handle,
|
||||
struct curl_waitfd extra_fds[],
|
||||
unsigned int extra_nfds,
|
||||
int timeout_ms,
|
||||
int *ret);
|
||||
|
||||
/*
|
||||
* Name: curl_multi_wakeup()
|
||||
*
|
||||
* Desc: wakes up a sleeping curl_multi_poll call.
|
||||
*
|
||||
* Returns: CURLMcode type, general multi error code.
|
||||
*/
|
||||
CURL_EXTERN CURLMcode curl_multi_wakeup(CURLM *multi_handle);
|
||||
|
||||
/*
|
||||
* Name: curl_multi_perform()
|
||||
*
|
||||
|
@ -242,7 +271,7 @@ CURL_EXTERN CURLMsg *curl_multi_info_read(CURLM *multi_handle,
|
|||
* value into the equivalent human readable error string. This is
|
||||
* useful for printing meaningful error messages.
|
||||
*
|
||||
* Returns: A pointer to a zero-terminated error message.
|
||||
* Returns: A pointer to a null-terminated error message.
|
||||
*/
|
||||
CURL_EXTERN const char *curl_multi_strerror(CURLMcode);
|
||||
|
||||
|
@ -289,16 +318,16 @@ typedef int (*curl_multi_timer_callback)(CURLM *multi, /* multi handle */
|
|||
void *userp); /* private callback
|
||||
pointer */
|
||||
|
||||
CURL_EXTERN CURLMcode curl_multi_socket(CURLM *multi_handle, curl_socket_t s,
|
||||
int *running_handles);
|
||||
CURL_EXTERN CURLMcode CURL_DEPRECATED(7.19.5, "Use curl_multi_socket_action()")
|
||||
curl_multi_socket(CURLM *multi_handle, curl_socket_t s, int *running_handles);
|
||||
|
||||
CURL_EXTERN CURLMcode curl_multi_socket_action(CURLM *multi_handle,
|
||||
curl_socket_t s,
|
||||
int ev_bitmask,
|
||||
int *running_handles);
|
||||
|
||||
CURL_EXTERN CURLMcode curl_multi_socket_all(CURLM *multi_handle,
|
||||
int *running_handles);
|
||||
CURL_EXTERN CURLMcode CURL_DEPRECATED(7.19.5, "Use curl_multi_socket_action()")
|
||||
curl_multi_socket_all(CURLM *multi_handle, int *running_handles);
|
||||
|
||||
#ifndef CURL_ALLOW_OLD_MULTI_SOCKET
|
||||
/* This macro below was added in 7.16.3 to push users who recompile to use
|
||||
|
@ -319,68 +348,56 @@ CURL_EXTERN CURLMcode curl_multi_socket_all(CURLM *multi_handle,
|
|||
CURL_EXTERN CURLMcode curl_multi_timeout(CURLM *multi_handle,
|
||||
long *milliseconds);
|
||||
|
||||
#undef CINIT /* re-using the same name as in curl.h */
|
||||
|
||||
#ifdef CURL_ISOCPP
|
||||
#define CINIT(name,type,num) CURLMOPT_ ## name = CURLOPTTYPE_ ## type + num
|
||||
#else
|
||||
/* The macro "##" is ISO C, we assume pre-ISO C doesn't support it. */
|
||||
#define LONG CURLOPTTYPE_LONG
|
||||
#define OBJECTPOINT CURLOPTTYPE_OBJECTPOINT
|
||||
#define FUNCTIONPOINT CURLOPTTYPE_FUNCTIONPOINT
|
||||
#define OFF_T CURLOPTTYPE_OFF_T
|
||||
#define CINIT(name,type,number) CURLMOPT_/**/name = type + number
|
||||
#endif
|
||||
|
||||
typedef enum {
|
||||
/* This is the socket callback function pointer */
|
||||
CINIT(SOCKETFUNCTION, FUNCTIONPOINT, 1),
|
||||
CURLOPT(CURLMOPT_SOCKETFUNCTION, CURLOPTTYPE_FUNCTIONPOINT, 1),
|
||||
|
||||
/* This is the argument passed to the socket callback */
|
||||
CINIT(SOCKETDATA, OBJECTPOINT, 2),
|
||||
CURLOPT(CURLMOPT_SOCKETDATA, CURLOPTTYPE_OBJECTPOINT, 2),
|
||||
|
||||
/* set to 1 to enable pipelining for this multi handle */
|
||||
CINIT(PIPELINING, LONG, 3),
|
||||
CURLOPT(CURLMOPT_PIPELINING, CURLOPTTYPE_LONG, 3),
|
||||
|
||||
/* This is the timer callback function pointer */
|
||||
CINIT(TIMERFUNCTION, FUNCTIONPOINT, 4),
|
||||
CURLOPT(CURLMOPT_TIMERFUNCTION, CURLOPTTYPE_FUNCTIONPOINT, 4),
|
||||
|
||||
/* This is the argument passed to the timer callback */
|
||||
CINIT(TIMERDATA, OBJECTPOINT, 5),
|
||||
CURLOPT(CURLMOPT_TIMERDATA, CURLOPTTYPE_OBJECTPOINT, 5),
|
||||
|
||||
/* maximum number of entries in the connection cache */
|
||||
CINIT(MAXCONNECTS, LONG, 6),
|
||||
CURLOPT(CURLMOPT_MAXCONNECTS, CURLOPTTYPE_LONG, 6),
|
||||
|
||||
/* maximum number of (pipelining) connections to one host */
|
||||
CINIT(MAX_HOST_CONNECTIONS, LONG, 7),
|
||||
CURLOPT(CURLMOPT_MAX_HOST_CONNECTIONS, CURLOPTTYPE_LONG, 7),
|
||||
|
||||
/* maximum number of requests in a pipeline */
|
||||
CINIT(MAX_PIPELINE_LENGTH, LONG, 8),
|
||||
CURLOPT(CURLMOPT_MAX_PIPELINE_LENGTH, CURLOPTTYPE_LONG, 8),
|
||||
|
||||
/* a connection with a content-length longer than this
|
||||
will not be considered for pipelining */
|
||||
CINIT(CONTENT_LENGTH_PENALTY_SIZE, OFF_T, 9),
|
||||
CURLOPT(CURLMOPT_CONTENT_LENGTH_PENALTY_SIZE, CURLOPTTYPE_OFF_T, 9),
|
||||
|
||||
/* a connection with a chunk length longer than this
|
||||
will not be considered for pipelining */
|
||||
CINIT(CHUNK_LENGTH_PENALTY_SIZE, OFF_T, 10),
|
||||
CURLOPT(CURLMOPT_CHUNK_LENGTH_PENALTY_SIZE, CURLOPTTYPE_OFF_T, 10),
|
||||
|
||||
/* a list of site names(+port) that are blacklisted from
|
||||
pipelining */
|
||||
CINIT(PIPELINING_SITE_BL, OBJECTPOINT, 11),
|
||||
/* a list of site names(+port) that are blocked from pipelining */
|
||||
CURLOPT(CURLMOPT_PIPELINING_SITE_BL, CURLOPTTYPE_OBJECTPOINT, 11),
|
||||
|
||||
/* a list of server types that are blacklisted from
|
||||
pipelining */
|
||||
CINIT(PIPELINING_SERVER_BL, OBJECTPOINT, 12),
|
||||
/* a list of server types that are blocked from pipelining */
|
||||
CURLOPT(CURLMOPT_PIPELINING_SERVER_BL, CURLOPTTYPE_OBJECTPOINT, 12),
|
||||
|
||||
/* maximum number of open connections in total */
|
||||
CINIT(MAX_TOTAL_CONNECTIONS, LONG, 13),
|
||||
CURLOPT(CURLMOPT_MAX_TOTAL_CONNECTIONS, CURLOPTTYPE_LONG, 13),
|
||||
|
||||
/* This is the server push callback function pointer */
|
||||
CINIT(PUSHFUNCTION, FUNCTIONPOINT, 14),
|
||||
CURLOPT(CURLMOPT_PUSHFUNCTION, CURLOPTTYPE_FUNCTIONPOINT, 14),
|
||||
|
||||
/* This is the argument passed to the server push callback */
|
||||
CINIT(PUSHDATA, OBJECTPOINT, 15),
|
||||
CURLOPT(CURLMOPT_PUSHDATA, CURLOPTTYPE_OBJECTPOINT, 15),
|
||||
|
||||
/* maximum number of concurrent streams to support on a connection */
|
||||
CURLOPT(CURLMOPT_MAX_CONCURRENT_STREAMS, CURLOPTTYPE_LONG, 16),
|
||||
|
||||
CURLMOPT_LASTENTRY /* the last unused */
|
||||
} CURLMoption;
|
||||
|
@ -414,12 +431,14 @@ CURL_EXTERN CURLMcode curl_multi_assign(CURLM *multi_handle,
|
|||
* Name: curl_push_callback
|
||||
*
|
||||
* Desc: This callback gets called when a new stream is being pushed by the
|
||||
* server. It approves or denies the new stream.
|
||||
* server. It approves or denies the new stream. It can also decide
|
||||
* to completely fail the connection.
|
||||
*
|
||||
* Returns: CURL_PUSH_OK or CURL_PUSH_DENY.
|
||||
* Returns: CURL_PUSH_OK, CURL_PUSH_DENY or CURL_PUSH_ERROROUT
|
||||
*/
|
||||
#define CURL_PUSH_OK 0
|
||||
#define CURL_PUSH_DENY 1
|
||||
#define CURL_PUSH_OK 0
|
||||
#define CURL_PUSH_DENY 1
|
||||
#define CURL_PUSH_ERROROUT 2 /* added in 7.72.0 */
|
||||
|
||||
struct curl_pushheaders; /* forward declaration only */
|
||||
|
||||
|
|
70
src/dependencies/cmcurl/include/curl/options.h
Normal file
70
src/dependencies/cmcurl/include/curl/options.h
Normal file
|
@ -0,0 +1,70 @@
|
|||
#ifndef CURLINC_OPTIONS_H
|
||||
#define CURLINC_OPTIONS_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef enum {
|
||||
CURLOT_LONG, /* long (a range of values) */
|
||||
CURLOT_VALUES, /* (a defined set or bitmask) */
|
||||
CURLOT_OFF_T, /* curl_off_t (a range of values) */
|
||||
CURLOT_OBJECT, /* pointer (void *) */
|
||||
CURLOT_STRING, /* (char * to null-terminated buffer) */
|
||||
CURLOT_SLIST, /* (struct curl_slist *) */
|
||||
CURLOT_CBPTR, /* (void * passed as-is to a callback) */
|
||||
CURLOT_BLOB, /* blob (struct curl_blob *) */
|
||||
CURLOT_FUNCTION /* function pointer */
|
||||
} curl_easytype;
|
||||
|
||||
/* Flag bits */
|
||||
|
||||
/* "alias" means it is provided for old programs to remain functional,
|
||||
we prefer another name */
|
||||
#define CURLOT_FLAG_ALIAS (1<<0)
|
||||
|
||||
/* The CURLOPTTYPE_* id ranges can still be used to figure out what type/size
|
||||
to use for curl_easy_setopt() for the given id */
|
||||
struct curl_easyoption {
|
||||
const char *name;
|
||||
CURLoption id;
|
||||
curl_easytype type;
|
||||
unsigned int flags;
|
||||
};
|
||||
|
||||
CURL_EXTERN const struct curl_easyoption *
|
||||
curl_easy_option_by_name(const char *name);
|
||||
|
||||
CURL_EXTERN const struct curl_easyoption *
|
||||
curl_easy_option_by_id(CURLoption id);
|
||||
|
||||
CURL_EXTERN const struct curl_easyoption *
|
||||
curl_easy_option_next(const struct curl_easyoption *prev);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} /* end of extern "C" */
|
||||
#endif
|
||||
#endif /* CURLINC_OPTIONS_H */
|
|
@ -1,5 +1,5 @@
|
|||
#ifndef __STDC_HEADERS_H
|
||||
#define __STDC_HEADERS_H
|
||||
#ifndef CURLINC_STDCHEADERS_H
|
||||
#define CURLINC_STDCHEADERS_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2016, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include <sys/types.h>
|
||||
|
@ -30,4 +32,4 @@ size_t fwrite(const void *, size_t, size_t, FILE *);
|
|||
int strcasecmp(const char *, const char *);
|
||||
int strncasecmp(const char *, const char *, size_t);
|
||||
|
||||
#endif /* __STDC_HEADERS_H */
|
||||
#endif /* CURLINC_STDCHEADERS_H */
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
#ifndef __CURL_SYSTEM_H
|
||||
#define __CURL_SYSTEM_H
|
||||
#ifndef CURLINC_SYSTEM_H
|
||||
#define CURLINC_SYSTEM_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2017, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/*
|
||||
|
@ -98,22 +100,6 @@
|
|||
# define CURL_SUFFIX_CURL_OFF_TU UL
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T int
|
||||
|
||||
#elif defined(__WATCOMC__)
|
||||
# if defined(__386__)
|
||||
# define CURL_TYPEOF_CURL_OFF_T __int64
|
||||
# define CURL_FORMAT_CURL_OFF_T "I64d"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "I64u"
|
||||
# define CURL_SUFFIX_CURL_OFF_T i64
|
||||
# define CURL_SUFFIX_CURL_OFF_TU ui64
|
||||
# else
|
||||
# define CURL_TYPEOF_CURL_OFF_T long
|
||||
# define CURL_FORMAT_CURL_OFF_T "ld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "lu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T L
|
||||
# define CURL_SUFFIX_CURL_OFF_TU UL
|
||||
# endif
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T int
|
||||
|
||||
#elif defined(__POCC__)
|
||||
# if (__POCC__ < 280)
|
||||
# define CURL_TYPEOF_CURL_OFF_T long
|
||||
|
@ -137,15 +123,26 @@
|
|||
# define CURL_TYPEOF_CURL_SOCKLEN_T int
|
||||
|
||||
#elif defined(__LCC__)
|
||||
# define CURL_TYPEOF_CURL_OFF_T long
|
||||
# define CURL_FORMAT_CURL_OFF_T "ld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "lu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T L
|
||||
# define CURL_SUFFIX_CURL_OFF_TU UL
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T int
|
||||
# if defined(__MCST__) /* MCST eLbrus Compiler Collection */
|
||||
# define CURL_TYPEOF_CURL_OFF_T long
|
||||
# define CURL_FORMAT_CURL_OFF_T "ld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "lu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T L
|
||||
# define CURL_SUFFIX_CURL_OFF_TU UL
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T socklen_t
|
||||
# define CURL_PULL_SYS_TYPES_H 1
|
||||
# define CURL_PULL_SYS_SOCKET_H 1
|
||||
# else /* Local (or Little) C Compiler */
|
||||
# define CURL_TYPEOF_CURL_OFF_T long
|
||||
# define CURL_FORMAT_CURL_OFF_T "ld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "lu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T L
|
||||
# define CURL_SUFFIX_CURL_OFF_TU UL
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T int
|
||||
# endif
|
||||
|
||||
#elif defined(__SYMBIAN32__)
|
||||
# if defined(__EABI__) /* Treat all ARM compilers equally */
|
||||
# if defined(__EABI__) /* Treat all ARM compilers equally */
|
||||
# define CURL_TYPEOF_CURL_OFF_T long long
|
||||
# define CURL_FORMAT_CURL_OFF_T "lld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "llu"
|
||||
|
@ -167,13 +164,33 @@
|
|||
# endif
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T unsigned int
|
||||
|
||||
#elif defined(__MWERKS__)
|
||||
#elif defined(macintosh)
|
||||
# include <ConditionalMacros.h>
|
||||
# if TYPE_LONGLONG
|
||||
# define CURL_TYPEOF_CURL_OFF_T long long
|
||||
# define CURL_FORMAT_CURL_OFF_T "lld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "llu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T LL
|
||||
# define CURL_SUFFIX_CURL_OFF_TU ULL
|
||||
# else
|
||||
# define CURL_TYPEOF_CURL_OFF_T long
|
||||
# define CURL_FORMAT_CURL_OFF_T "ld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "lu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T L
|
||||
# define CURL_SUFFIX_CURL_OFF_TU UL
|
||||
# endif
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T unsigned int
|
||||
|
||||
#elif defined(__TANDEM)
|
||||
# if ! defined(__LP64)
|
||||
/* Required for 32-bit NonStop builds only. */
|
||||
# define CURL_TYPEOF_CURL_OFF_T long long
|
||||
# define CURL_FORMAT_CURL_OFF_T "lld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "llu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T LL
|
||||
# define CURL_SUFFIX_CURL_OFF_TU ULL
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T int
|
||||
# endif
|
||||
|
||||
#elif defined(_WIN32_WCE)
|
||||
# define CURL_TYPEOF_CURL_OFF_T __int64
|
||||
|
@ -210,16 +227,14 @@
|
|||
# define CURL_TYPEOF_CURL_SOCKLEN_T unsigned int
|
||||
|
||||
#elif defined(__OS400__)
|
||||
# if defined(__ILEC400__)
|
||||
# define CURL_TYPEOF_CURL_OFF_T long long
|
||||
# define CURL_FORMAT_CURL_OFF_T "lld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "llu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T LL
|
||||
# define CURL_SUFFIX_CURL_OFF_TU ULL
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T socklen_t
|
||||
# define CURL_PULL_SYS_TYPES_H 1
|
||||
# define CURL_PULL_SYS_SOCKET_H 1
|
||||
# endif
|
||||
# define CURL_TYPEOF_CURL_OFF_T long long
|
||||
# define CURL_FORMAT_CURL_OFF_T "lld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "llu"
|
||||
# define CURL_SUFFIX_CURL_OFF_T LL
|
||||
# define CURL_SUFFIX_CURL_OFF_TU ULL
|
||||
# define CURL_TYPEOF_CURL_SOCKLEN_T socklen_t
|
||||
# define CURL_PULL_SYS_TYPES_H 1
|
||||
# define CURL_PULL_SYS_SOCKET_H 1
|
||||
|
||||
#elif defined(__MVS__)
|
||||
# if defined(__IBMC__) || defined(__IBMCPP__)
|
||||
|
@ -288,7 +303,6 @@
|
|||
# define CURL_TYPEOF_CURL_SOCKLEN_T int
|
||||
|
||||
#elif defined(__TINYC__) /* also known as tcc */
|
||||
|
||||
# define CURL_TYPEOF_CURL_OFF_T long long
|
||||
# define CURL_FORMAT_CURL_OFF_T "lld"
|
||||
# define CURL_FORMAT_CURL_OFF_TU "llu"
|
||||
|
@ -377,6 +391,7 @@
|
|||
# define CURL_SUFFIX_CURL_OFF_TU ULL
|
||||
# elif defined(__LP64__) || \
|
||||
defined(__x86_64__) || defined(__ppc64__) || defined(__sparc64__) || \
|
||||
defined(__e2k__) || \
|
||||
(defined(__SIZEOF_LONG__) && __SIZEOF_LONG__ == 8) || \
|
||||
(defined(__LONG_MAX__) && __LONG_MAX__ == 9223372036854775807L)
|
||||
# define CURL_TYPEOF_CURL_OFF_T long
|
||||
|
@ -473,21 +488,21 @@
|
|||
*/
|
||||
|
||||
#if defined(__BORLANDC__) && (__BORLANDC__ == 0x0551)
|
||||
# define __CURL_OFF_T_C_HLPR2(x) x
|
||||
# define __CURL_OFF_T_C_HLPR1(x) __CURL_OFF_T_C_HLPR2(x)
|
||||
# define CURL_OFF_T_C(Val) __CURL_OFF_T_C_HLPR1(Val) ## \
|
||||
__CURL_OFF_T_C_HLPR1(CURL_SUFFIX_CURL_OFF_T)
|
||||
# define CURL_OFF_TU_C(Val) __CURL_OFF_T_C_HLPR1(Val) ## \
|
||||
__CURL_OFF_T_C_HLPR1(CURL_SUFFIX_CURL_OFF_TU)
|
||||
# define CURLINC_OFF_T_C_HLPR2(x) x
|
||||
# define CURLINC_OFF_T_C_HLPR1(x) CURLINC_OFF_T_C_HLPR2(x)
|
||||
# define CURL_OFF_T_C(Val) CURLINC_OFF_T_C_HLPR1(Val) ## \
|
||||
CURLINC_OFF_T_C_HLPR1(CURL_SUFFIX_CURL_OFF_T)
|
||||
# define CURL_OFF_TU_C(Val) CURLINC_OFF_T_C_HLPR1(Val) ## \
|
||||
CURLINC_OFF_T_C_HLPR1(CURL_SUFFIX_CURL_OFF_TU)
|
||||
#else
|
||||
# ifdef CURL_ISOCPP
|
||||
# define __CURL_OFF_T_C_HLPR2(Val,Suffix) Val ## Suffix
|
||||
# define CURLINC_OFF_T_C_HLPR2(Val,Suffix) Val ## Suffix
|
||||
# else
|
||||
# define __CURL_OFF_T_C_HLPR2(Val,Suffix) Val/**/Suffix
|
||||
# define CURLINC_OFF_T_C_HLPR2(Val,Suffix) Val/**/Suffix
|
||||
# endif
|
||||
# define __CURL_OFF_T_C_HLPR1(Val,Suffix) __CURL_OFF_T_C_HLPR2(Val,Suffix)
|
||||
# define CURL_OFF_T_C(Val) __CURL_OFF_T_C_HLPR1(Val,CURL_SUFFIX_CURL_OFF_T)
|
||||
# define CURL_OFF_TU_C(Val) __CURL_OFF_T_C_HLPR1(Val,CURL_SUFFIX_CURL_OFF_TU)
|
||||
# define CURLINC_OFF_T_C_HLPR1(Val,Suffix) CURLINC_OFF_T_C_HLPR2(Val,Suffix)
|
||||
# define CURL_OFF_T_C(Val) CURLINC_OFF_T_C_HLPR1(Val,CURL_SUFFIX_CURL_OFF_T)
|
||||
# define CURL_OFF_TU_C(Val) CURLINC_OFF_T_C_HLPR1(Val,CURL_SUFFIX_CURL_OFF_TU)
|
||||
#endif
|
||||
|
||||
#endif /* __CURL_SYSTEM_H */
|
||||
#endif /* CURLINC_SYSTEM_H */
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
#ifndef __CURL_TYPECHECK_GCC_H
|
||||
#define __CURL_TYPECHECK_GCC_H
|
||||
#ifndef CURLINC_TYPECHECK_GCC_H
|
||||
#define CURLINC_TYPECHECK_GCC_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,15 +20,17 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/* wraps curl_easy_setopt() with typechecking */
|
||||
|
||||
/* To add a new kind of warning, add an
|
||||
* if(_curl_is_sometype_option(_curl_opt))
|
||||
* if(!_curl_is_sometype(value))
|
||||
* if(curlcheck_sometype_option(_curl_opt))
|
||||
* if(!curlcheck_sometype(value))
|
||||
* _curl_easy_setopt_err_sometype();
|
||||
* block and define _curl_is_sometype_option, _curl_is_sometype and
|
||||
* block and define curlcheck_sometype_option, curlcheck_sometype and
|
||||
* _curl_easy_setopt_err_sometype below
|
||||
*
|
||||
* NOTE: We use two nested 'if' statements here instead of the && operator, in
|
||||
|
@ -38,112 +40,116 @@
|
|||
* To add an option that uses the same type as an existing option, you'll just
|
||||
* need to extend the appropriate _curl_*_option macro
|
||||
*/
|
||||
#define curl_easy_setopt(handle, option, value) \
|
||||
__extension__ ({ \
|
||||
__typeof__(option) _curl_opt = option; \
|
||||
if(__builtin_constant_p(_curl_opt)) { \
|
||||
if(_curl_is_long_option(_curl_opt)) \
|
||||
if(!_curl_is_long(value)) \
|
||||
_curl_easy_setopt_err_long(); \
|
||||
if(_curl_is_off_t_option(_curl_opt)) \
|
||||
if(!_curl_is_off_t(value)) \
|
||||
_curl_easy_setopt_err_curl_off_t(); \
|
||||
if(_curl_is_string_option(_curl_opt)) \
|
||||
if(!_curl_is_string(value)) \
|
||||
_curl_easy_setopt_err_string(); \
|
||||
if(_curl_is_write_cb_option(_curl_opt)) \
|
||||
if(!_curl_is_write_cb(value)) \
|
||||
_curl_easy_setopt_err_write_callback(); \
|
||||
if((_curl_opt) == CURLOPT_RESOLVER_START_FUNCTION) \
|
||||
if(!_curl_is_resolver_start_callback(value)) \
|
||||
_curl_easy_setopt_err_resolver_start_callback(); \
|
||||
if((_curl_opt) == CURLOPT_READFUNCTION) \
|
||||
if(!_curl_is_read_cb(value)) \
|
||||
_curl_easy_setopt_err_read_cb(); \
|
||||
if((_curl_opt) == CURLOPT_IOCTLFUNCTION) \
|
||||
if(!_curl_is_ioctl_cb(value)) \
|
||||
_curl_easy_setopt_err_ioctl_cb(); \
|
||||
if((_curl_opt) == CURLOPT_SOCKOPTFUNCTION) \
|
||||
if(!_curl_is_sockopt_cb(value)) \
|
||||
_curl_easy_setopt_err_sockopt_cb(); \
|
||||
if((_curl_opt) == CURLOPT_OPENSOCKETFUNCTION) \
|
||||
if(!_curl_is_opensocket_cb(value)) \
|
||||
_curl_easy_setopt_err_opensocket_cb(); \
|
||||
if((_curl_opt) == CURLOPT_PROGRESSFUNCTION) \
|
||||
if(!_curl_is_progress_cb(value)) \
|
||||
_curl_easy_setopt_err_progress_cb(); \
|
||||
if((_curl_opt) == CURLOPT_DEBUGFUNCTION) \
|
||||
if(!_curl_is_debug_cb(value)) \
|
||||
_curl_easy_setopt_err_debug_cb(); \
|
||||
if((_curl_opt) == CURLOPT_SSL_CTX_FUNCTION) \
|
||||
if(!_curl_is_ssl_ctx_cb(value)) \
|
||||
_curl_easy_setopt_err_ssl_ctx_cb(); \
|
||||
if(_curl_is_conv_cb_option(_curl_opt)) \
|
||||
if(!_curl_is_conv_cb(value)) \
|
||||
_curl_easy_setopt_err_conv_cb(); \
|
||||
if((_curl_opt) == CURLOPT_SEEKFUNCTION) \
|
||||
if(!_curl_is_seek_cb(value)) \
|
||||
_curl_easy_setopt_err_seek_cb(); \
|
||||
if(_curl_is_cb_data_option(_curl_opt)) \
|
||||
if(!_curl_is_cb_data(value)) \
|
||||
_curl_easy_setopt_err_cb_data(); \
|
||||
if((_curl_opt) == CURLOPT_ERRORBUFFER) \
|
||||
if(!_curl_is_error_buffer(value)) \
|
||||
_curl_easy_setopt_err_error_buffer(); \
|
||||
if((_curl_opt) == CURLOPT_STDERR) \
|
||||
if(!_curl_is_FILE(value)) \
|
||||
_curl_easy_setopt_err_FILE(); \
|
||||
if(_curl_is_postfields_option(_curl_opt)) \
|
||||
if(!_curl_is_postfields(value)) \
|
||||
_curl_easy_setopt_err_postfields(); \
|
||||
if((_curl_opt) == CURLOPT_HTTPPOST) \
|
||||
if(!_curl_is_arr((value), struct curl_httppost)) \
|
||||
_curl_easy_setopt_err_curl_httpost(); \
|
||||
if((_curl_opt) == CURLOPT_MIMEPOST) \
|
||||
if(!_curl_is_ptr((value), curl_mime)) \
|
||||
_curl_easy_setopt_err_curl_mimepost(); \
|
||||
if(_curl_is_slist_option(_curl_opt)) \
|
||||
if(!_curl_is_arr((value), struct curl_slist)) \
|
||||
_curl_easy_setopt_err_curl_slist(); \
|
||||
if((_curl_opt) == CURLOPT_SHARE) \
|
||||
if(!_curl_is_ptr((value), CURLSH)) \
|
||||
_curl_easy_setopt_err_CURLSH(); \
|
||||
} \
|
||||
curl_easy_setopt(handle, _curl_opt, value); \
|
||||
})
|
||||
#define curl_easy_setopt(handle, option, value) \
|
||||
__extension__({ \
|
||||
CURLoption _curl_opt = (option); \
|
||||
if(__builtin_constant_p(_curl_opt)) { \
|
||||
CURL_IGNORE_DEPRECATION( \
|
||||
if(curlcheck_long_option(_curl_opt)) \
|
||||
if(!curlcheck_long(value)) \
|
||||
_curl_easy_setopt_err_long(); \
|
||||
if(curlcheck_off_t_option(_curl_opt)) \
|
||||
if(!curlcheck_off_t(value)) \
|
||||
_curl_easy_setopt_err_curl_off_t(); \
|
||||
if(curlcheck_string_option(_curl_opt)) \
|
||||
if(!curlcheck_string(value)) \
|
||||
_curl_easy_setopt_err_string(); \
|
||||
if(curlcheck_write_cb_option(_curl_opt)) \
|
||||
if(!curlcheck_write_cb(value)) \
|
||||
_curl_easy_setopt_err_write_callback(); \
|
||||
if((_curl_opt) == CURLOPT_RESOLVER_START_FUNCTION) \
|
||||
if(!curlcheck_resolver_start_callback(value)) \
|
||||
_curl_easy_setopt_err_resolver_start_callback(); \
|
||||
if((_curl_opt) == CURLOPT_READFUNCTION) \
|
||||
if(!curlcheck_read_cb(value)) \
|
||||
_curl_easy_setopt_err_read_cb(); \
|
||||
if((_curl_opt) == CURLOPT_IOCTLFUNCTION) \
|
||||
if(!curlcheck_ioctl_cb(value)) \
|
||||
_curl_easy_setopt_err_ioctl_cb(); \
|
||||
if((_curl_opt) == CURLOPT_SOCKOPTFUNCTION) \
|
||||
if(!curlcheck_sockopt_cb(value)) \
|
||||
_curl_easy_setopt_err_sockopt_cb(); \
|
||||
if((_curl_opt) == CURLOPT_OPENSOCKETFUNCTION) \
|
||||
if(!curlcheck_opensocket_cb(value)) \
|
||||
_curl_easy_setopt_err_opensocket_cb(); \
|
||||
if((_curl_opt) == CURLOPT_PROGRESSFUNCTION) \
|
||||
if(!curlcheck_progress_cb(value)) \
|
||||
_curl_easy_setopt_err_progress_cb(); \
|
||||
if((_curl_opt) == CURLOPT_DEBUGFUNCTION) \
|
||||
if(!curlcheck_debug_cb(value)) \
|
||||
_curl_easy_setopt_err_debug_cb(); \
|
||||
if((_curl_opt) == CURLOPT_SSL_CTX_FUNCTION) \
|
||||
if(!curlcheck_ssl_ctx_cb(value)) \
|
||||
_curl_easy_setopt_err_ssl_ctx_cb(); \
|
||||
if(curlcheck_conv_cb_option(_curl_opt)) \
|
||||
if(!curlcheck_conv_cb(value)) \
|
||||
_curl_easy_setopt_err_conv_cb(); \
|
||||
if((_curl_opt) == CURLOPT_SEEKFUNCTION) \
|
||||
if(!curlcheck_seek_cb(value)) \
|
||||
_curl_easy_setopt_err_seek_cb(); \
|
||||
if(curlcheck_cb_data_option(_curl_opt)) \
|
||||
if(!curlcheck_cb_data(value)) \
|
||||
_curl_easy_setopt_err_cb_data(); \
|
||||
if((_curl_opt) == CURLOPT_ERRORBUFFER) \
|
||||
if(!curlcheck_error_buffer(value)) \
|
||||
_curl_easy_setopt_err_error_buffer(); \
|
||||
if((_curl_opt) == CURLOPT_STDERR) \
|
||||
if(!curlcheck_FILE(value)) \
|
||||
_curl_easy_setopt_err_FILE(); \
|
||||
if(curlcheck_postfields_option(_curl_opt)) \
|
||||
if(!curlcheck_postfields(value)) \
|
||||
_curl_easy_setopt_err_postfields(); \
|
||||
if((_curl_opt) == CURLOPT_HTTPPOST) \
|
||||
if(!curlcheck_arr((value), struct curl_httppost)) \
|
||||
_curl_easy_setopt_err_curl_httpost(); \
|
||||
if((_curl_opt) == CURLOPT_MIMEPOST) \
|
||||
if(!curlcheck_ptr((value), curl_mime)) \
|
||||
_curl_easy_setopt_err_curl_mimepost(); \
|
||||
if(curlcheck_slist_option(_curl_opt)) \
|
||||
if(!curlcheck_arr((value), struct curl_slist)) \
|
||||
_curl_easy_setopt_err_curl_slist(); \
|
||||
if((_curl_opt) == CURLOPT_SHARE) \
|
||||
if(!curlcheck_ptr((value), CURLSH)) \
|
||||
_curl_easy_setopt_err_CURLSH(); \
|
||||
) \
|
||||
} \
|
||||
curl_easy_setopt(handle, _curl_opt, value); \
|
||||
})
|
||||
|
||||
/* wraps curl_easy_getinfo() with typechecking */
|
||||
#define curl_easy_getinfo(handle, info, arg) \
|
||||
__extension__ ({ \
|
||||
__typeof__(info) _curl_info = info; \
|
||||
if(__builtin_constant_p(_curl_info)) { \
|
||||
if(_curl_is_string_info(_curl_info)) \
|
||||
if(!_curl_is_arr((arg), char *)) \
|
||||
_curl_easy_getinfo_err_string(); \
|
||||
if(_curl_is_long_info(_curl_info)) \
|
||||
if(!_curl_is_arr((arg), long)) \
|
||||
_curl_easy_getinfo_err_long(); \
|
||||
if(_curl_is_double_info(_curl_info)) \
|
||||
if(!_curl_is_arr((arg), double)) \
|
||||
_curl_easy_getinfo_err_double(); \
|
||||
if(_curl_is_slist_info(_curl_info)) \
|
||||
if(!_curl_is_arr((arg), struct curl_slist *)) \
|
||||
_curl_easy_getinfo_err_curl_slist(); \
|
||||
if(_curl_is_tlssessioninfo_info(_curl_info)) \
|
||||
if(!_curl_is_arr((arg), struct curl_tlssessioninfo *)) \
|
||||
_curl_easy_getinfo_err_curl_tlssesssioninfo(); \
|
||||
if(_curl_is_certinfo_info(_curl_info)) \
|
||||
if(!_curl_is_arr((arg), struct curl_certinfo *)) \
|
||||
_curl_easy_getinfo_err_curl_certinfo(); \
|
||||
if(_curl_is_socket_info(_curl_info)) \
|
||||
if(!_curl_is_arr((arg), curl_socket_t)) \
|
||||
_curl_easy_getinfo_err_curl_socket(); \
|
||||
if(_curl_is_off_t_info(_curl_info)) \
|
||||
if(!_curl_is_arr((arg), curl_off_t)) \
|
||||
_curl_easy_getinfo_err_curl_off_t(); \
|
||||
} \
|
||||
curl_easy_getinfo(handle, _curl_info, arg); \
|
||||
})
|
||||
#define curl_easy_getinfo(handle, info, arg) \
|
||||
__extension__({ \
|
||||
CURLINFO _curl_info = (info); \
|
||||
if(__builtin_constant_p(_curl_info)) { \
|
||||
CURL_IGNORE_DEPRECATION( \
|
||||
if(curlcheck_string_info(_curl_info)) \
|
||||
if(!curlcheck_arr((arg), char *)) \
|
||||
_curl_easy_getinfo_err_string(); \
|
||||
if(curlcheck_long_info(_curl_info)) \
|
||||
if(!curlcheck_arr((arg), long)) \
|
||||
_curl_easy_getinfo_err_long(); \
|
||||
if(curlcheck_double_info(_curl_info)) \
|
||||
if(!curlcheck_arr((arg), double)) \
|
||||
_curl_easy_getinfo_err_double(); \
|
||||
if(curlcheck_slist_info(_curl_info)) \
|
||||
if(!curlcheck_arr((arg), struct curl_slist *)) \
|
||||
_curl_easy_getinfo_err_curl_slist(); \
|
||||
if(curlcheck_tlssessioninfo_info(_curl_info)) \
|
||||
if(!curlcheck_arr((arg), struct curl_tlssessioninfo *)) \
|
||||
_curl_easy_getinfo_err_curl_tlssesssioninfo(); \
|
||||
if(curlcheck_certinfo_info(_curl_info)) \
|
||||
if(!curlcheck_arr((arg), struct curl_certinfo *)) \
|
||||
_curl_easy_getinfo_err_curl_certinfo(); \
|
||||
if(curlcheck_socket_info(_curl_info)) \
|
||||
if(!curlcheck_arr((arg), curl_socket_t)) \
|
||||
_curl_easy_getinfo_err_curl_socket(); \
|
||||
if(curlcheck_off_t_info(_curl_info)) \
|
||||
if(!curlcheck_arr((arg), curl_off_t)) \
|
||||
_curl_easy_getinfo_err_curl_off_t(); \
|
||||
) \
|
||||
} \
|
||||
curl_easy_getinfo(handle, _curl_info, arg); \
|
||||
})
|
||||
|
||||
/*
|
||||
* For now, just make sure that the functions are called with three arguments
|
||||
|
@ -156,83 +162,83 @@ __extension__ ({ \
|
|||
* functions */
|
||||
|
||||
/* To define a new warning, use _CURL_WARNING(identifier, "message") */
|
||||
#define _CURL_WARNING(id, message) \
|
||||
static void __attribute__((__warning__(message))) \
|
||||
__attribute__((__unused__)) __attribute__((__noinline__)) \
|
||||
#define CURLWARNING(id, message) \
|
||||
static void __attribute__((__warning__(message))) \
|
||||
__attribute__((__unused__)) __attribute__((__noinline__)) \
|
||||
id(void) { __asm__(""); }
|
||||
|
||||
_CURL_WARNING(_curl_easy_setopt_err_long,
|
||||
CURLWARNING(_curl_easy_setopt_err_long,
|
||||
"curl_easy_setopt expects a long argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_curl_off_t,
|
||||
CURLWARNING(_curl_easy_setopt_err_curl_off_t,
|
||||
"curl_easy_setopt expects a curl_off_t argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_string,
|
||||
CURLWARNING(_curl_easy_setopt_err_string,
|
||||
"curl_easy_setopt expects a "
|
||||
"string ('char *' or char[]) argument for this option"
|
||||
)
|
||||
_CURL_WARNING(_curl_easy_setopt_err_write_callback,
|
||||
CURLWARNING(_curl_easy_setopt_err_write_callback,
|
||||
"curl_easy_setopt expects a curl_write_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_resolver_start_callback,
|
||||
CURLWARNING(_curl_easy_setopt_err_resolver_start_callback,
|
||||
"curl_easy_setopt expects a "
|
||||
"curl_resolver_start_callback argument for this option"
|
||||
)
|
||||
_CURL_WARNING(_curl_easy_setopt_err_read_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_read_cb,
|
||||
"curl_easy_setopt expects a curl_read_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_ioctl_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_ioctl_cb,
|
||||
"curl_easy_setopt expects a curl_ioctl_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_sockopt_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_sockopt_cb,
|
||||
"curl_easy_setopt expects a curl_sockopt_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_opensocket_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_opensocket_cb,
|
||||
"curl_easy_setopt expects a "
|
||||
"curl_opensocket_callback argument for this option"
|
||||
)
|
||||
_CURL_WARNING(_curl_easy_setopt_err_progress_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_progress_cb,
|
||||
"curl_easy_setopt expects a curl_progress_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_debug_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_debug_cb,
|
||||
"curl_easy_setopt expects a curl_debug_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_ssl_ctx_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_ssl_ctx_cb,
|
||||
"curl_easy_setopt expects a curl_ssl_ctx_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_conv_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_conv_cb,
|
||||
"curl_easy_setopt expects a curl_conv_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_seek_cb,
|
||||
CURLWARNING(_curl_easy_setopt_err_seek_cb,
|
||||
"curl_easy_setopt expects a curl_seek_callback argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_cb_data,
|
||||
CURLWARNING(_curl_easy_setopt_err_cb_data,
|
||||
"curl_easy_setopt expects a "
|
||||
"private data pointer as argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_error_buffer,
|
||||
CURLWARNING(_curl_easy_setopt_err_error_buffer,
|
||||
"curl_easy_setopt expects a "
|
||||
"char buffer of CURL_ERROR_SIZE as argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_FILE,
|
||||
CURLWARNING(_curl_easy_setopt_err_FILE,
|
||||
"curl_easy_setopt expects a 'FILE *' argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_postfields,
|
||||
CURLWARNING(_curl_easy_setopt_err_postfields,
|
||||
"curl_easy_setopt expects a 'void *' or 'char *' argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_curl_httpost,
|
||||
CURLWARNING(_curl_easy_setopt_err_curl_httpost,
|
||||
"curl_easy_setopt expects a 'struct curl_httppost *' "
|
||||
"argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_curl_mimepost,
|
||||
CURLWARNING(_curl_easy_setopt_err_curl_mimepost,
|
||||
"curl_easy_setopt expects a 'curl_mime *' "
|
||||
"argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_curl_slist,
|
||||
CURLWARNING(_curl_easy_setopt_err_curl_slist,
|
||||
"curl_easy_setopt expects a 'struct curl_slist *' argument for this option")
|
||||
_CURL_WARNING(_curl_easy_setopt_err_CURLSH,
|
||||
CURLWARNING(_curl_easy_setopt_err_CURLSH,
|
||||
"curl_easy_setopt expects a CURLSH* argument for this option")
|
||||
|
||||
_CURL_WARNING(_curl_easy_getinfo_err_string,
|
||||
CURLWARNING(_curl_easy_getinfo_err_string,
|
||||
"curl_easy_getinfo expects a pointer to 'char *' for this info")
|
||||
_CURL_WARNING(_curl_easy_getinfo_err_long,
|
||||
CURLWARNING(_curl_easy_getinfo_err_long,
|
||||
"curl_easy_getinfo expects a pointer to long for this info")
|
||||
_CURL_WARNING(_curl_easy_getinfo_err_double,
|
||||
CURLWARNING(_curl_easy_getinfo_err_double,
|
||||
"curl_easy_getinfo expects a pointer to double for this info")
|
||||
_CURL_WARNING(_curl_easy_getinfo_err_curl_slist,
|
||||
CURLWARNING(_curl_easy_getinfo_err_curl_slist,
|
||||
"curl_easy_getinfo expects a pointer to 'struct curl_slist *' for this info")
|
||||
_CURL_WARNING(_curl_easy_getinfo_err_curl_tlssesssioninfo,
|
||||
CURLWARNING(_curl_easy_getinfo_err_curl_tlssesssioninfo,
|
||||
"curl_easy_getinfo expects a pointer to "
|
||||
"'struct curl_tlssessioninfo *' for this info")
|
||||
_CURL_WARNING(_curl_easy_getinfo_err_curl_certinfo,
|
||||
CURLWARNING(_curl_easy_getinfo_err_curl_certinfo,
|
||||
"curl_easy_getinfo expects a pointer to "
|
||||
"'struct curl_certinfo *' for this info")
|
||||
_CURL_WARNING(_curl_easy_getinfo_err_curl_socket,
|
||||
CURLWARNING(_curl_easy_getinfo_err_curl_socket,
|
||||
"curl_easy_getinfo expects a pointer to curl_socket_t for this info")
|
||||
_CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
||||
CURLWARNING(_curl_easy_getinfo_err_curl_off_t,
|
||||
"curl_easy_getinfo expects a pointer to curl_off_t for this info")
|
||||
|
||||
/* groups of curl_easy_setops options that take the same type of argument */
|
||||
|
@ -244,14 +250,14 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
*/
|
||||
|
||||
/* evaluates to true if option takes a long argument */
|
||||
#define _curl_is_long_option(option) \
|
||||
#define curlcheck_long_option(option) \
|
||||
(0 < (option) && (option) < CURLOPTTYPE_OBJECTPOINT)
|
||||
|
||||
#define _curl_is_off_t_option(option) \
|
||||
((option) > CURLOPTTYPE_OFF_T)
|
||||
#define curlcheck_off_t_option(option) \
|
||||
(((option) > CURLOPTTYPE_OFF_T) && ((option) < CURLOPTTYPE_BLOB))
|
||||
|
||||
/* evaluates to true if option takes a char* argument */
|
||||
#define _curl_is_string_option(option) \
|
||||
#define curlcheck_string_option(option) \
|
||||
((option) == CURLOPT_ABSTRACT_UNIX_SOCKET || \
|
||||
(option) == CURLOPT_ACCEPT_ENCODING || \
|
||||
(option) == CURLOPT_ALTSVC || \
|
||||
|
@ -270,9 +276,10 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
(option) == CURLOPT_DNS_SERVERS || \
|
||||
(option) == CURLOPT_DOH_URL || \
|
||||
(option) == CURLOPT_EGDSOCKET || \
|
||||
(option) == CURLOPT_FTPPORT || \
|
||||
(option) == CURLOPT_FTP_ACCOUNT || \
|
||||
(option) == CURLOPT_FTP_ALTERNATIVE_TO_USER || \
|
||||
(option) == CURLOPT_FTPPORT || \
|
||||
(option) == CURLOPT_HSTS || \
|
||||
(option) == CURLOPT_INTERFACE || \
|
||||
(option) == CURLOPT_ISSUERCERT || \
|
||||
(option) == CURLOPT_KEYPASSWD || \
|
||||
|
@ -285,33 +292,40 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
(option) == CURLOPT_PASSWORD || \
|
||||
(option) == CURLOPT_PINNEDPUBLICKEY || \
|
||||
(option) == CURLOPT_PRE_PROXY || \
|
||||
(option) == CURLOPT_PROTOCOLS_STR || \
|
||||
(option) == CURLOPT_PROXY || \
|
||||
(option) == CURLOPT_PROXYPASSWORD || \
|
||||
(option) == CURLOPT_PROXYUSERNAME || \
|
||||
(option) == CURLOPT_PROXYUSERPWD || \
|
||||
(option) == CURLOPT_PROXY_CAINFO || \
|
||||
(option) == CURLOPT_PROXY_CAPATH || \
|
||||
(option) == CURLOPT_PROXY_CRLFILE || \
|
||||
(option) == CURLOPT_PROXY_ISSUERCERT || \
|
||||
(option) == CURLOPT_PROXY_KEYPASSWD || \
|
||||
(option) == CURLOPT_PROXY_PINNEDPUBLICKEY || \
|
||||
(option) == CURLOPT_PROXY_SERVICE_NAME || \
|
||||
(option) == CURLOPT_PROXY_SSL_CIPHER_LIST || \
|
||||
(option) == CURLOPT_PROXY_SSLCERT || \
|
||||
(option) == CURLOPT_PROXY_SSLCERTTYPE || \
|
||||
(option) == CURLOPT_PROXY_SSLKEY || \
|
||||
(option) == CURLOPT_PROXY_SSLKEYTYPE || \
|
||||
(option) == CURLOPT_PROXY_SSL_CIPHER_LIST || \
|
||||
(option) == CURLOPT_PROXY_TLS13_CIPHERS || \
|
||||
(option) == CURLOPT_PROXY_TLSAUTH_PASSWORD || \
|
||||
(option) == CURLOPT_PROXY_TLSAUTH_USERNAME || \
|
||||
(option) == CURLOPT_PROXY_TLSAUTH_TYPE || \
|
||||
(option) == CURLOPT_PROXY_TLSAUTH_USERNAME || \
|
||||
(option) == CURLOPT_PROXYPASSWORD || \
|
||||
(option) == CURLOPT_PROXYUSERNAME || \
|
||||
(option) == CURLOPT_PROXYUSERPWD || \
|
||||
(option) == CURLOPT_RANDOM_FILE || \
|
||||
(option) == CURLOPT_RANGE || \
|
||||
(option) == CURLOPT_REDIR_PROTOCOLS_STR || \
|
||||
(option) == CURLOPT_REFERER || \
|
||||
(option) == CURLOPT_REQUEST_TARGET || \
|
||||
(option) == CURLOPT_RTSP_SESSION_ID || \
|
||||
(option) == CURLOPT_RTSP_STREAM_URI || \
|
||||
(option) == CURLOPT_RTSP_TRANSPORT || \
|
||||
(option) == CURLOPT_SASL_AUTHZID || \
|
||||
(option) == CURLOPT_SERVICE_NAME || \
|
||||
(option) == CURLOPT_SOCKS5_GSSAPI_SERVICE || \
|
||||
(option) == CURLOPT_SSH_HOST_PUBLIC_KEY_MD5 || \
|
||||
(option) == CURLOPT_SSH_HOST_PUBLIC_KEY_SHA256 || \
|
||||
(option) == CURLOPT_SSH_KNOWNHOSTS || \
|
||||
(option) == CURLOPT_SSH_PRIVATE_KEYFILE || \
|
||||
(option) == CURLOPT_SSH_PUBLIC_KEYFILE || \
|
||||
|
@ -321,6 +335,7 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
(option) == CURLOPT_SSLKEY || \
|
||||
(option) == CURLOPT_SSLKEYTYPE || \
|
||||
(option) == CURLOPT_SSL_CIPHER_LIST || \
|
||||
(option) == CURLOPT_TLS13_CIPHERS || \
|
||||
(option) == CURLOPT_TLSAUTH_PASSWORD || \
|
||||
(option) == CURLOPT_TLSAUTH_TYPE || \
|
||||
(option) == CURLOPT_TLSAUTH_USERNAME || \
|
||||
|
@ -328,32 +343,36 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
(option) == CURLOPT_URL || \
|
||||
(option) == CURLOPT_USERAGENT || \
|
||||
(option) == CURLOPT_USERNAME || \
|
||||
(option) == CURLOPT_AWS_SIGV4 || \
|
||||
(option) == CURLOPT_USERPWD || \
|
||||
(option) == CURLOPT_XOAUTH2_BEARER || \
|
||||
(option) == CURLOPT_SSL_EC_CURVES || \
|
||||
0)
|
||||
|
||||
/* evaluates to true if option takes a curl_write_callback argument */
|
||||
#define _curl_is_write_cb_option(option) \
|
||||
((option) == CURLOPT_HEADERFUNCTION || \
|
||||
#define curlcheck_write_cb_option(option) \
|
||||
((option) == CURLOPT_HEADERFUNCTION || \
|
||||
(option) == CURLOPT_WRITEFUNCTION)
|
||||
|
||||
/* evaluates to true if option takes a curl_conv_callback argument */
|
||||
#define _curl_is_conv_cb_option(option) \
|
||||
((option) == CURLOPT_CONV_TO_NETWORK_FUNCTION || \
|
||||
(option) == CURLOPT_CONV_FROM_NETWORK_FUNCTION || \
|
||||
#define curlcheck_conv_cb_option(option) \
|
||||
((option) == CURLOPT_CONV_TO_NETWORK_FUNCTION || \
|
||||
(option) == CURLOPT_CONV_FROM_NETWORK_FUNCTION || \
|
||||
(option) == CURLOPT_CONV_FROM_UTF8_FUNCTION)
|
||||
|
||||
/* evaluates to true if option takes a data argument to pass to a callback */
|
||||
#define _curl_is_cb_data_option(option) \
|
||||
#define curlcheck_cb_data_option(option) \
|
||||
((option) == CURLOPT_CHUNK_DATA || \
|
||||
(option) == CURLOPT_CLOSESOCKETDATA || \
|
||||
(option) == CURLOPT_DEBUGDATA || \
|
||||
(option) == CURLOPT_FNMATCH_DATA || \
|
||||
(option) == CURLOPT_HEADERDATA || \
|
||||
(option) == CURLOPT_HSTSREADDATA || \
|
||||
(option) == CURLOPT_HSTSWRITEDATA || \
|
||||
(option) == CURLOPT_INTERLEAVEDATA || \
|
||||
(option) == CURLOPT_IOCTLDATA || \
|
||||
(option) == CURLOPT_OPENSOCKETDATA || \
|
||||
(option) == CURLOPT_PRIVATE || \
|
||||
(option) == CURLOPT_PREREQDATA || \
|
||||
(option) == CURLOPT_PROGRESSDATA || \
|
||||
(option) == CURLOPT_READDATA || \
|
||||
(option) == CURLOPT_SEEKDATA || \
|
||||
|
@ -362,17 +381,18 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
(option) == CURLOPT_SSL_CTX_DATA || \
|
||||
(option) == CURLOPT_WRITEDATA || \
|
||||
(option) == CURLOPT_RESOLVER_START_DATA || \
|
||||
(option) == CURLOPT_CURLU || \
|
||||
(option) == CURLOPT_TRAILERDATA || \
|
||||
(option) == CURLOPT_SSH_HOSTKEYDATA || \
|
||||
0)
|
||||
|
||||
/* evaluates to true if option takes a POST data argument (void* or char*) */
|
||||
#define _curl_is_postfields_option(option) \
|
||||
#define curlcheck_postfields_option(option) \
|
||||
((option) == CURLOPT_POSTFIELDS || \
|
||||
(option) == CURLOPT_COPYPOSTFIELDS || \
|
||||
0)
|
||||
|
||||
/* evaluates to true if option takes a struct curl_slist * argument */
|
||||
#define _curl_is_slist_option(option) \
|
||||
#define curlcheck_slist_option(option) \
|
||||
((option) == CURLOPT_HTTP200ALIASES || \
|
||||
(option) == CURLOPT_HTTPHEADER || \
|
||||
(option) == CURLOPT_MAIL_RCPT || \
|
||||
|
@ -382,45 +402,47 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
(option) == CURLOPT_QUOTE || \
|
||||
(option) == CURLOPT_RESOLVE || \
|
||||
(option) == CURLOPT_TELNETOPTIONS || \
|
||||
(option) == CURLOPT_CONNECT_TO || \
|
||||
0)
|
||||
|
||||
/* groups of curl_easy_getinfo infos that take the same type of argument */
|
||||
|
||||
/* evaluates to true if info expects a pointer to char * argument */
|
||||
#define _curl_is_string_info(info) \
|
||||
(CURLINFO_STRING < (info) && (info) < CURLINFO_LONG)
|
||||
#define curlcheck_string_info(info) \
|
||||
(CURLINFO_STRING < (info) && (info) < CURLINFO_LONG && \
|
||||
(info) != CURLINFO_PRIVATE)
|
||||
|
||||
/* evaluates to true if info expects a pointer to long argument */
|
||||
#define _curl_is_long_info(info) \
|
||||
#define curlcheck_long_info(info) \
|
||||
(CURLINFO_LONG < (info) && (info) < CURLINFO_DOUBLE)
|
||||
|
||||
/* evaluates to true if info expects a pointer to double argument */
|
||||
#define _curl_is_double_info(info) \
|
||||
#define curlcheck_double_info(info) \
|
||||
(CURLINFO_DOUBLE < (info) && (info) < CURLINFO_SLIST)
|
||||
|
||||
/* true if info expects a pointer to struct curl_slist * argument */
|
||||
#define _curl_is_slist_info(info) \
|
||||
#define curlcheck_slist_info(info) \
|
||||
(((info) == CURLINFO_SSL_ENGINES) || ((info) == CURLINFO_COOKIELIST))
|
||||
|
||||
/* true if info expects a pointer to struct curl_tlssessioninfo * argument */
|
||||
#define _curl_is_tlssessioninfo_info(info) \
|
||||
#define curlcheck_tlssessioninfo_info(info) \
|
||||
(((info) == CURLINFO_TLS_SSL_PTR) || ((info) == CURLINFO_TLS_SESSION))
|
||||
|
||||
/* true if info expects a pointer to struct curl_certinfo * argument */
|
||||
#define _curl_is_certinfo_info(info) ((info) == CURLINFO_CERTINFO)
|
||||
#define curlcheck_certinfo_info(info) ((info) == CURLINFO_CERTINFO)
|
||||
|
||||
/* true if info expects a pointer to struct curl_socket_t argument */
|
||||
#define _curl_is_socket_info(info) \
|
||||
#define curlcheck_socket_info(info) \
|
||||
(CURLINFO_SOCKET < (info) && (info) < CURLINFO_OFF_T)
|
||||
|
||||
/* true if info expects a pointer to curl_off_t argument */
|
||||
#define _curl_is_off_t_info(info) \
|
||||
#define curlcheck_off_t_info(info) \
|
||||
(CURLINFO_OFF_T < (info))
|
||||
|
||||
|
||||
/* typecheck helpers -- check whether given expression has requested type*/
|
||||
/* typecheck helpers -- check whether given expression has requested type */
|
||||
|
||||
/* For pointers, you can use the _curl_is_ptr/_curl_is_arr macros,
|
||||
/* For pointers, you can use the curlcheck_ptr/curlcheck_arr macros,
|
||||
* otherwise define a new macro. Search for __builtin_types_compatible_p
|
||||
* in the GCC manual.
|
||||
* NOTE: these macros MUST NOT EVALUATE their arguments! The argument is
|
||||
|
@ -430,35 +452,35 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
*/
|
||||
|
||||
/* XXX: should evaluate to true if expr is a pointer */
|
||||
#define _curl_is_any_ptr(expr) \
|
||||
#define curlcheck_any_ptr(expr) \
|
||||
(sizeof(expr) == sizeof(void *))
|
||||
|
||||
/* evaluates to true if expr is NULL */
|
||||
/* XXX: must not evaluate expr, so this check is not accurate */
|
||||
#define _curl_is_NULL(expr) \
|
||||
#define curlcheck_NULL(expr) \
|
||||
(__builtin_types_compatible_p(__typeof__(expr), __typeof__(NULL)))
|
||||
|
||||
/* evaluates to true if expr is type*, const type* or NULL */
|
||||
#define _curl_is_ptr(expr, type) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), type *) || \
|
||||
#define curlcheck_ptr(expr, type) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), type *) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), const type *))
|
||||
|
||||
/* evaluates to true if expr is one of type[], type*, NULL or const type* */
|
||||
#define _curl_is_arr(expr, type) \
|
||||
(_curl_is_ptr((expr), type) || \
|
||||
#define curlcheck_arr(expr, type) \
|
||||
(curlcheck_ptr((expr), type) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), type []))
|
||||
|
||||
/* evaluates to true if expr is a string */
|
||||
#define _curl_is_string(expr) \
|
||||
(_curl_is_arr((expr), char) || \
|
||||
_curl_is_arr((expr), signed char) || \
|
||||
_curl_is_arr((expr), unsigned char))
|
||||
#define curlcheck_string(expr) \
|
||||
(curlcheck_arr((expr), char) || \
|
||||
curlcheck_arr((expr), signed char) || \
|
||||
curlcheck_arr((expr), unsigned char))
|
||||
|
||||
/* evaluates to true if expr is a long (no matter the signedness)
|
||||
* XXX: for now, int is also accepted (and therefore short and char, which
|
||||
* are promoted to int when passed to a variadic function) */
|
||||
#define _curl_is_long(expr) \
|
||||
#define curlcheck_long(expr) \
|
||||
(__builtin_types_compatible_p(__typeof__(expr), long) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), signed long) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), unsigned long) || \
|
||||
|
@ -473,59 +495,59 @@ _CURL_WARNING(_curl_easy_getinfo_err_curl_off_t,
|
|||
__builtin_types_compatible_p(__typeof__(expr), unsigned char))
|
||||
|
||||
/* evaluates to true if expr is of type curl_off_t */
|
||||
#define _curl_is_off_t(expr) \
|
||||
#define curlcheck_off_t(expr) \
|
||||
(__builtin_types_compatible_p(__typeof__(expr), curl_off_t))
|
||||
|
||||
/* evaluates to true if expr is abuffer suitable for CURLOPT_ERRORBUFFER */
|
||||
/* XXX: also check size of an char[] array? */
|
||||
#define _curl_is_error_buffer(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), char *) || \
|
||||
#define curlcheck_error_buffer(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), char *) || \
|
||||
__builtin_types_compatible_p(__typeof__(expr), char[]))
|
||||
|
||||
/* evaluates to true if expr is of type (const) void* or (const) FILE* */
|
||||
#if 0
|
||||
#define _curl_is_cb_data(expr) \
|
||||
(_curl_is_ptr((expr), void) || \
|
||||
_curl_is_ptr((expr), FILE))
|
||||
#define curlcheck_cb_data(expr) \
|
||||
(curlcheck_ptr((expr), void) || \
|
||||
curlcheck_ptr((expr), FILE))
|
||||
#else /* be less strict */
|
||||
#define _curl_is_cb_data(expr) \
|
||||
_curl_is_any_ptr(expr)
|
||||
#define curlcheck_cb_data(expr) \
|
||||
curlcheck_any_ptr(expr)
|
||||
#endif
|
||||
|
||||
/* evaluates to true if expr is of type FILE* */
|
||||
#define _curl_is_FILE(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
#define curlcheck_FILE(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
(__builtin_types_compatible_p(__typeof__(expr), FILE *)))
|
||||
|
||||
/* evaluates to true if expr can be passed as POST data (void* or char*) */
|
||||
#define _curl_is_postfields(expr) \
|
||||
(_curl_is_ptr((expr), void) || \
|
||||
_curl_is_arr((expr), char) || \
|
||||
_curl_is_arr((expr), unsigned char))
|
||||
#define curlcheck_postfields(expr) \
|
||||
(curlcheck_ptr((expr), void) || \
|
||||
curlcheck_arr((expr), char) || \
|
||||
curlcheck_arr((expr), unsigned char))
|
||||
|
||||
/* helper: __builtin_types_compatible_p distinguishes between functions and
|
||||
* function pointers, hide it */
|
||||
#define _curl_callback_compatible(func, type) \
|
||||
(__builtin_types_compatible_p(__typeof__(func), type) || \
|
||||
#define curlcheck_cb_compatible(func, type) \
|
||||
(__builtin_types_compatible_p(__typeof__(func), type) || \
|
||||
__builtin_types_compatible_p(__typeof__(func) *, type))
|
||||
|
||||
/* evaluates to true if expr is of type curl_resolver_start_callback */
|
||||
#define _curl_is_resolver_start_callback(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_resolver_start_callback))
|
||||
#define curlcheck_resolver_start_callback(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_resolver_start_callback))
|
||||
|
||||
/* evaluates to true if expr is of type curl_read_callback or "similar" */
|
||||
#define _curl_is_read_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), __typeof__(fread) *) || \
|
||||
_curl_callback_compatible((expr), curl_read_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_read_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_read_callback2) || \
|
||||
_curl_callback_compatible((expr), _curl_read_callback3) || \
|
||||
_curl_callback_compatible((expr), _curl_read_callback4) || \
|
||||
_curl_callback_compatible((expr), _curl_read_callback5) || \
|
||||
_curl_callback_compatible((expr), _curl_read_callback6))
|
||||
#define curlcheck_read_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), __typeof__(fread) *) || \
|
||||
curlcheck_cb_compatible((expr), curl_read_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_read_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_read_callback2) || \
|
||||
curlcheck_cb_compatible((expr), _curl_read_callback3) || \
|
||||
curlcheck_cb_compatible((expr), _curl_read_callback4) || \
|
||||
curlcheck_cb_compatible((expr), _curl_read_callback5) || \
|
||||
curlcheck_cb_compatible((expr), _curl_read_callback6))
|
||||
typedef size_t (*_curl_read_callback1)(char *, size_t, size_t, void *);
|
||||
typedef size_t (*_curl_read_callback2)(char *, size_t, size_t, const void *);
|
||||
typedef size_t (*_curl_read_callback3)(char *, size_t, size_t, FILE *);
|
||||
|
@ -534,16 +556,16 @@ typedef size_t (*_curl_read_callback5)(void *, size_t, size_t, const void *);
|
|||
typedef size_t (*_curl_read_callback6)(void *, size_t, size_t, FILE *);
|
||||
|
||||
/* evaluates to true if expr is of type curl_write_callback or "similar" */
|
||||
#define _curl_is_write_cb(expr) \
|
||||
(_curl_is_read_cb(expr) || \
|
||||
_curl_callback_compatible((expr), __typeof__(fwrite) *) || \
|
||||
_curl_callback_compatible((expr), curl_write_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_write_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_write_callback2) || \
|
||||
_curl_callback_compatible((expr), _curl_write_callback3) || \
|
||||
_curl_callback_compatible((expr), _curl_write_callback4) || \
|
||||
_curl_callback_compatible((expr), _curl_write_callback5) || \
|
||||
_curl_callback_compatible((expr), _curl_write_callback6))
|
||||
#define curlcheck_write_cb(expr) \
|
||||
(curlcheck_read_cb(expr) || \
|
||||
curlcheck_cb_compatible((expr), __typeof__(fwrite) *) || \
|
||||
curlcheck_cb_compatible((expr), curl_write_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_write_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_write_callback2) || \
|
||||
curlcheck_cb_compatible((expr), _curl_write_callback3) || \
|
||||
curlcheck_cb_compatible((expr), _curl_write_callback4) || \
|
||||
curlcheck_cb_compatible((expr), _curl_write_callback5) || \
|
||||
curlcheck_cb_compatible((expr), _curl_write_callback6))
|
||||
typedef size_t (*_curl_write_callback1)(const char *, size_t, size_t, void *);
|
||||
typedef size_t (*_curl_write_callback2)(const char *, size_t, size_t,
|
||||
const void *);
|
||||
|
@ -554,37 +576,37 @@ typedef size_t (*_curl_write_callback5)(const void *, size_t, size_t,
|
|||
typedef size_t (*_curl_write_callback6)(const void *, size_t, size_t, FILE *);
|
||||
|
||||
/* evaluates to true if expr is of type curl_ioctl_callback or "similar" */
|
||||
#define _curl_is_ioctl_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_ioctl_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_ioctl_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_ioctl_callback2) || \
|
||||
_curl_callback_compatible((expr), _curl_ioctl_callback3) || \
|
||||
_curl_callback_compatible((expr), _curl_ioctl_callback4))
|
||||
#define curlcheck_ioctl_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_ioctl_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ioctl_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ioctl_callback2) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ioctl_callback3) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ioctl_callback4))
|
||||
typedef curlioerr (*_curl_ioctl_callback1)(CURL *, int, void *);
|
||||
typedef curlioerr (*_curl_ioctl_callback2)(CURL *, int, const void *);
|
||||
typedef curlioerr (*_curl_ioctl_callback3)(CURL *, curliocmd, void *);
|
||||
typedef curlioerr (*_curl_ioctl_callback4)(CURL *, curliocmd, const void *);
|
||||
|
||||
/* evaluates to true if expr is of type curl_sockopt_callback or "similar" */
|
||||
#define _curl_is_sockopt_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_sockopt_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_sockopt_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_sockopt_callback2))
|
||||
#define curlcheck_sockopt_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_sockopt_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_sockopt_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_sockopt_callback2))
|
||||
typedef int (*_curl_sockopt_callback1)(void *, curl_socket_t, curlsocktype);
|
||||
typedef int (*_curl_sockopt_callback2)(const void *, curl_socket_t,
|
||||
curlsocktype);
|
||||
|
||||
/* evaluates to true if expr is of type curl_opensocket_callback or
|
||||
"similar" */
|
||||
#define _curl_is_opensocket_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_opensocket_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_opensocket_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_opensocket_callback2) || \
|
||||
_curl_callback_compatible((expr), _curl_opensocket_callback3) || \
|
||||
_curl_callback_compatible((expr), _curl_opensocket_callback4))
|
||||
#define curlcheck_opensocket_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_opensocket_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_opensocket_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_opensocket_callback2) || \
|
||||
curlcheck_cb_compatible((expr), _curl_opensocket_callback3) || \
|
||||
curlcheck_cb_compatible((expr), _curl_opensocket_callback4))
|
||||
typedef curl_socket_t (*_curl_opensocket_callback1)
|
||||
(void *, curlsocktype, struct curl_sockaddr *);
|
||||
typedef curl_socket_t (*_curl_opensocket_callback2)
|
||||
|
@ -595,28 +617,28 @@ typedef curl_socket_t (*_curl_opensocket_callback4)
|
|||
(const void *, curlsocktype, const struct curl_sockaddr *);
|
||||
|
||||
/* evaluates to true if expr is of type curl_progress_callback or "similar" */
|
||||
#define _curl_is_progress_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_progress_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_progress_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_progress_callback2))
|
||||
#define curlcheck_progress_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_progress_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_progress_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_progress_callback2))
|
||||
typedef int (*_curl_progress_callback1)(void *,
|
||||
double, double, double, double);
|
||||
typedef int (*_curl_progress_callback2)(const void *,
|
||||
double, double, double, double);
|
||||
|
||||
/* evaluates to true if expr is of type curl_debug_callback or "similar" */
|
||||
#define _curl_is_debug_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_debug_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_debug_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_debug_callback2) || \
|
||||
_curl_callback_compatible((expr), _curl_debug_callback3) || \
|
||||
_curl_callback_compatible((expr), _curl_debug_callback4) || \
|
||||
_curl_callback_compatible((expr), _curl_debug_callback5) || \
|
||||
_curl_callback_compatible((expr), _curl_debug_callback6) || \
|
||||
_curl_callback_compatible((expr), _curl_debug_callback7) || \
|
||||
_curl_callback_compatible((expr), _curl_debug_callback8))
|
||||
#define curlcheck_debug_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_debug_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_debug_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_debug_callback2) || \
|
||||
curlcheck_cb_compatible((expr), _curl_debug_callback3) || \
|
||||
curlcheck_cb_compatible((expr), _curl_debug_callback4) || \
|
||||
curlcheck_cb_compatible((expr), _curl_debug_callback5) || \
|
||||
curlcheck_cb_compatible((expr), _curl_debug_callback6) || \
|
||||
curlcheck_cb_compatible((expr), _curl_debug_callback7) || \
|
||||
curlcheck_cb_compatible((expr), _curl_debug_callback8))
|
||||
typedef int (*_curl_debug_callback1) (CURL *,
|
||||
curl_infotype, char *, size_t, void *);
|
||||
typedef int (*_curl_debug_callback2) (CURL *,
|
||||
|
@ -636,17 +658,17 @@ typedef int (*_curl_debug_callback8) (CURL *,
|
|||
|
||||
/* evaluates to true if expr is of type curl_ssl_ctx_callback or "similar" */
|
||||
/* this is getting even messier... */
|
||||
#define _curl_is_ssl_ctx_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_ssl_ctx_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_ssl_ctx_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_ssl_ctx_callback2) || \
|
||||
_curl_callback_compatible((expr), _curl_ssl_ctx_callback3) || \
|
||||
_curl_callback_compatible((expr), _curl_ssl_ctx_callback4) || \
|
||||
_curl_callback_compatible((expr), _curl_ssl_ctx_callback5) || \
|
||||
_curl_callback_compatible((expr), _curl_ssl_ctx_callback6) || \
|
||||
_curl_callback_compatible((expr), _curl_ssl_ctx_callback7) || \
|
||||
_curl_callback_compatible((expr), _curl_ssl_ctx_callback8))
|
||||
#define curlcheck_ssl_ctx_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_ssl_ctx_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ssl_ctx_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ssl_ctx_callback2) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ssl_ctx_callback3) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ssl_ctx_callback4) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ssl_ctx_callback5) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ssl_ctx_callback6) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ssl_ctx_callback7) || \
|
||||
curlcheck_cb_compatible((expr), _curl_ssl_ctx_callback8))
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback1)(CURL *, void *, void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback2)(CURL *, void *, const void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback3)(CURL *, const void *, void *);
|
||||
|
@ -656,11 +678,11 @@ typedef CURLcode (*_curl_ssl_ctx_callback4)(CURL *, const void *,
|
|||
/* hack: if we included OpenSSL's ssl.h, we know about SSL_CTX
|
||||
* this will of course break if we're included before OpenSSL headers...
|
||||
*/
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback5)(CURL *, SSL_CTX, void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback6)(CURL *, SSL_CTX, const void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback7)(CURL *, const SSL_CTX, void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback8)(CURL *, const SSL_CTX,
|
||||
const void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback5)(CURL *, SSL_CTX *, void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback6)(CURL *, SSL_CTX *, const void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback7)(CURL *, const SSL_CTX *, void *);
|
||||
typedef CURLcode (*_curl_ssl_ctx_callback8)(CURL *, const SSL_CTX *,
|
||||
const void *);
|
||||
#else
|
||||
typedef _curl_ssl_ctx_callback1 _curl_ssl_ctx_callback5;
|
||||
typedef _curl_ssl_ctx_callback1 _curl_ssl_ctx_callback6;
|
||||
|
@ -669,26 +691,26 @@ typedef _curl_ssl_ctx_callback1 _curl_ssl_ctx_callback8;
|
|||
#endif
|
||||
|
||||
/* evaluates to true if expr is of type curl_conv_callback or "similar" */
|
||||
#define _curl_is_conv_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_conv_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_conv_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_conv_callback2) || \
|
||||
_curl_callback_compatible((expr), _curl_conv_callback3) || \
|
||||
_curl_callback_compatible((expr), _curl_conv_callback4))
|
||||
#define curlcheck_conv_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_conv_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_conv_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_conv_callback2) || \
|
||||
curlcheck_cb_compatible((expr), _curl_conv_callback3) || \
|
||||
curlcheck_cb_compatible((expr), _curl_conv_callback4))
|
||||
typedef CURLcode (*_curl_conv_callback1)(char *, size_t length);
|
||||
typedef CURLcode (*_curl_conv_callback2)(const char *, size_t length);
|
||||
typedef CURLcode (*_curl_conv_callback3)(void *, size_t length);
|
||||
typedef CURLcode (*_curl_conv_callback4)(const void *, size_t length);
|
||||
|
||||
/* evaluates to true if expr is of type curl_seek_callback or "similar" */
|
||||
#define _curl_is_seek_cb(expr) \
|
||||
(_curl_is_NULL(expr) || \
|
||||
_curl_callback_compatible((expr), curl_seek_callback) || \
|
||||
_curl_callback_compatible((expr), _curl_seek_callback1) || \
|
||||
_curl_callback_compatible((expr), _curl_seek_callback2))
|
||||
#define curlcheck_seek_cb(expr) \
|
||||
(curlcheck_NULL(expr) || \
|
||||
curlcheck_cb_compatible((expr), curl_seek_callback) || \
|
||||
curlcheck_cb_compatible((expr), _curl_seek_callback1) || \
|
||||
curlcheck_cb_compatible((expr), _curl_seek_callback2))
|
||||
typedef CURLcode (*_curl_seek_callback1)(void *, curl_off_t, int);
|
||||
typedef CURLcode (*_curl_seek_callback2)(const void *, curl_off_t, int);
|
||||
|
||||
|
||||
#endif /* __CURL_TYPECHECK_GCC_H */
|
||||
#endif /* CURLINC_TYPECHECK_GCC_H */
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
#ifndef __CURL_URLAPI_H
|
||||
#define __CURL_URLAPI_H
|
||||
#ifndef CURLINC_URLAPI_H
|
||||
#define CURLINC_URLAPI_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2018 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl.h"
|
||||
|
@ -47,7 +49,21 @@ typedef enum {
|
|||
CURLUE_NO_HOST, /* 14 */
|
||||
CURLUE_NO_PORT, /* 15 */
|
||||
CURLUE_NO_QUERY, /* 16 */
|
||||
CURLUE_NO_FRAGMENT /* 17 */
|
||||
CURLUE_NO_FRAGMENT, /* 17 */
|
||||
CURLUE_NO_ZONEID, /* 18 */
|
||||
CURLUE_BAD_FILE_URL, /* 19 */
|
||||
CURLUE_BAD_FRAGMENT, /* 20 */
|
||||
CURLUE_BAD_HOSTNAME, /* 21 */
|
||||
CURLUE_BAD_IPV6, /* 22 */
|
||||
CURLUE_BAD_LOGIN, /* 23 */
|
||||
CURLUE_BAD_PASSWORD, /* 24 */
|
||||
CURLUE_BAD_PATH, /* 25 */
|
||||
CURLUE_BAD_QUERY, /* 26 */
|
||||
CURLUE_BAD_SCHEME, /* 27 */
|
||||
CURLUE_BAD_SLASHES, /* 28 */
|
||||
CURLUE_BAD_USER, /* 29 */
|
||||
CURLUE_LACKS_IDN, /* 30 */
|
||||
CURLUE_LAST
|
||||
} CURLUcode;
|
||||
|
||||
typedef enum {
|
||||
|
@ -77,6 +93,10 @@ typedef enum {
|
|||
#define CURLU_URLENCODE (1<<7) /* URL encode on set */
|
||||
#define CURLU_APPENDQUERY (1<<8) /* append a form style part */
|
||||
#define CURLU_GUESS_SCHEME (1<<9) /* legacy curl-style guessing */
|
||||
#define CURLU_NO_AUTHORITY (1<<10) /* Allow empty authority when the
|
||||
scheme is unknown. */
|
||||
#define CURLU_ALLOW_SPACE (1<<11) /* Allow spaces in the URL */
|
||||
#define CURLU_PUNYCODE (1<<12) /* get the host name in pynycode */
|
||||
|
||||
typedef struct Curl_URL CURLU;
|
||||
|
||||
|
@ -97,14 +117,14 @@ CURL_EXTERN void curl_url_cleanup(CURLU *handle);
|
|||
* curl_url_dup() duplicates a CURLU handle and returns a new copy. The new
|
||||
* handle must also be freed with curl_url_cleanup().
|
||||
*/
|
||||
CURL_EXTERN CURLU *curl_url_dup(CURLU *in);
|
||||
CURL_EXTERN CURLU *curl_url_dup(const CURLU *in);
|
||||
|
||||
/*
|
||||
* curl_url_get() extracts a specific part of the URL from a CURLU
|
||||
* handle. Returns error code. The returned pointer MUST be freed with
|
||||
* curl_free() afterwards.
|
||||
*/
|
||||
CURL_EXTERN CURLUcode curl_url_get(CURLU *handle, CURLUPart what,
|
||||
CURL_EXTERN CURLUcode curl_url_get(const CURLU *handle, CURLUPart what,
|
||||
char **part, unsigned int flags);
|
||||
|
||||
/*
|
||||
|
@ -115,9 +135,15 @@ CURL_EXTERN CURLUcode curl_url_get(CURLU *handle, CURLUPart what,
|
|||
CURL_EXTERN CURLUcode curl_url_set(CURLU *handle, CURLUPart what,
|
||||
const char *part, unsigned int flags);
|
||||
|
||||
/*
|
||||
* curl_url_strerror() turns a CURLUcode value into the equivalent human
|
||||
* readable error string. This is useful for printing meaningful error
|
||||
* messages.
|
||||
*/
|
||||
CURL_EXTERN const char *curl_url_strerror(CURLUcode);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} /* end of extern "C" */
|
||||
#endif
|
||||
|
||||
#endif
|
||||
#endif /* CURLINC_URLAPI_H */
|
||||
|
|
84
src/dependencies/cmcurl/include/curl/websockets.h
Normal file
84
src/dependencies/cmcurl/include/curl/websockets.h
Normal file
|
@ -0,0 +1,84 @@
|
|||
#ifndef CURLINC_WEBSOCKETS_H
|
||||
#define CURLINC_WEBSOCKETS_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct curl_ws_frame {
|
||||
int age; /* zero */
|
||||
int flags; /* See the CURLWS_* defines */
|
||||
curl_off_t offset; /* the offset of this data into the frame */
|
||||
curl_off_t bytesleft; /* number of pending bytes left of the payload */
|
||||
size_t len; /* size of the current data chunk */
|
||||
};
|
||||
|
||||
/* flag bits */
|
||||
#define CURLWS_TEXT (1<<0)
|
||||
#define CURLWS_BINARY (1<<1)
|
||||
#define CURLWS_CONT (1<<2)
|
||||
#define CURLWS_CLOSE (1<<3)
|
||||
#define CURLWS_PING (1<<4)
|
||||
#define CURLWS_OFFSET (1<<5)
|
||||
|
||||
/*
|
||||
* NAME curl_ws_recv()
|
||||
*
|
||||
* DESCRIPTION
|
||||
*
|
||||
* Receives data from the websocket connection. Use after successful
|
||||
* curl_easy_perform() with CURLOPT_CONNECT_ONLY option.
|
||||
*/
|
||||
CURL_EXTERN CURLcode curl_ws_recv(CURL *curl, void *buffer, size_t buflen,
|
||||
size_t *recv,
|
||||
struct curl_ws_frame **metap);
|
||||
|
||||
/* sendflags for curl_ws_send() */
|
||||
#define CURLWS_PONG (1<<6)
|
||||
|
||||
/*
|
||||
* NAME curl_easy_send()
|
||||
*
|
||||
* DESCRIPTION
|
||||
*
|
||||
* Sends data over the websocket connection. Use after successful
|
||||
* curl_easy_perform() with CURLOPT_CONNECT_ONLY option.
|
||||
*/
|
||||
CURL_EXTERN CURLcode curl_ws_send(CURL *curl, const void *buffer,
|
||||
size_t buflen, size_t *sent,
|
||||
curl_off_t framesize,
|
||||
unsigned int sendflags);
|
||||
|
||||
/* bits for the CURLOPT_WS_OPTIONS bitmask: */
|
||||
#define CURLWS_RAW_MODE (1<<0)
|
||||
|
||||
CURL_EXTERN struct curl_ws_frame *curl_ws_meta(CURL *curl);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* CURLINC_WEBSOCKETS_H */
|
|
@ -1,4 +1,29 @@
|
|||
#***************************************************************************
|
||||
# _ _ ____ _
|
||||
# Project ___| | | | _ \| |
|
||||
# / __| | | | |_) | |
|
||||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
# furnished to do so, under the terms of the COPYING file.
|
||||
#
|
||||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
set(LIB_NAME cmcurl)
|
||||
set(LIBCURL_OUTPUT_NAME cmcurl)
|
||||
add_definitions(-DBUILDING_LIBCURL)
|
||||
|
||||
if(BUILD_SHARED_LIBS)
|
||||
set(CURL_STATICLIB NO)
|
||||
|
@ -18,43 +43,10 @@ list(APPEND HHEADERS
|
|||
${CMAKE_CURRENT_BINARY_DIR}/curl_config.h
|
||||
)
|
||||
|
||||
if(MSVC AND NOT CURL_STATICLIB)
|
||||
if(WIN32 AND NOT CURL_STATICLIB)
|
||||
list(APPEND CSOURCES libcurl.rc)
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /wd4127")
|
||||
endif()
|
||||
|
||||
# SET(CSOURCES
|
||||
# # memdebug.c -not used
|
||||
# # nwlib.c - Not used
|
||||
# # strtok.c - specify later
|
||||
# # strtoofft.c - specify later
|
||||
# )
|
||||
|
||||
# # if we have Kerberos 4, right now this is never on
|
||||
# #OPTION(CURL_KRB4 "Use Kerberos 4" OFF)
|
||||
# IF(CURL_KRB4)
|
||||
# SET(CSOURCES ${CSOURCES}
|
||||
# krb4.c
|
||||
# security.c
|
||||
# )
|
||||
# ENDIF(CURL_KRB4)
|
||||
|
||||
# #OPTION(CURL_MALLOC_DEBUG "Debug mallocs in Curl" OFF)
|
||||
# MARK_AS_ADVANCED(CURL_MALLOC_DEBUG)
|
||||
# IF(CURL_MALLOC_DEBUG)
|
||||
# SET(CSOURCES ${CSOURCES}
|
||||
# memdebug.c
|
||||
# )
|
||||
# ENDIF(CURL_MALLOC_DEBUG)
|
||||
|
||||
# # only build compat strtoofft if we need to
|
||||
# IF(NOT HAVE_STRTOLL AND NOT HAVE__STRTOI64)
|
||||
# SET(CSOURCES ${CSOURCES}
|
||||
# strtoofft.c
|
||||
# )
|
||||
# ENDIF(NOT HAVE_STRTOLL AND NOT HAVE__STRTOI64)
|
||||
|
||||
|
||||
# The rest of the build
|
||||
|
||||
include_directories(${CMAKE_CURRENT_BINARY_DIR}/../include)
|
||||
|
@ -70,7 +62,7 @@ endif()
|
|||
# For windows we want to install OPENSSL_LIBRARIES dlls
|
||||
# and also copy them into the build tree so that testing
|
||||
# can find them.
|
||||
if(CMAKE_USE_OPENSSL AND OPENSSL_FOUND AND WIN32)
|
||||
if(CURL_USE_OPENSSL AND OPENSSL_FOUND AND WIN32)
|
||||
find_file(CMAKE_EAY_DLL NAME libeay32.dll HINTS ${OPENSSL_INCLUDE_DIR}/..)
|
||||
find_file(CMAKE_SSL_DLL NAME ssleay32.dll HINTS ${OPENSSL_INCLUDE_DIR}/..)
|
||||
mark_as_advanced(CMAKE_EAY_DLL CMAKE_SSL_DLL)
|
||||
|
@ -97,21 +89,52 @@ add_library(
|
|||
${CMAKE_CURL_SSL_DLLS}
|
||||
)
|
||||
|
||||
add_library(
|
||||
${PROJECT_NAME}::${LIB_NAME}
|
||||
ALIAS ${LIB_NAME}
|
||||
)
|
||||
|
||||
if(NOT BUILD_SHARED_LIBS)
|
||||
set_target_properties(${LIB_NAME} PROPERTIES INTERFACE_COMPILE_DEFINITIONS CURL_STATICLIB)
|
||||
endif()
|
||||
|
||||
target_link_libraries(${LIB_NAME} ${CURL_LIBS})
|
||||
target_link_libraries(${LIB_NAME} PRIVATE ${CURL_LIBS})
|
||||
|
||||
if(0) # This code not needed for building within CMake.
|
||||
if(WIN32)
|
||||
add_definitions(-D_USRDLL)
|
||||
endif()
|
||||
transform_makefile_inc("Makefile.soname" "${CMAKE_CURRENT_BINARY_DIR}/Makefile.soname.cmake")
|
||||
include(${CMAKE_CURRENT_BINARY_DIR}/Makefile.soname.cmake)
|
||||
endif()
|
||||
|
||||
set_target_properties(${LIB_NAME} PROPERTIES COMPILE_DEFINITIONS BUILDING_LIBCURL)
|
||||
set_target_properties(${LIB_NAME} PROPERTIES
|
||||
COMPILE_DEFINITIONS BUILDING_LIBCURL
|
||||
OUTPUT_NAME ${LIBCURL_OUTPUT_NAME}
|
||||
)
|
||||
|
||||
if(0) # This code not needed for building within CMake.
|
||||
if(CMAKE_SYSTEM_NAME STREQUAL "AIX" OR
|
||||
CMAKE_SYSTEM_NAME STREQUAL "Linux" OR
|
||||
CMAKE_SYSTEM_NAME STREQUAL "Darwin" OR
|
||||
CMAKE_SYSTEM_NAME STREQUAL "GNU/kFreeBSD" OR
|
||||
|
||||
# FreeBSD comes with the a.out and elf flavours
|
||||
# but a.out was supported up to version 3.x and
|
||||
# elf from 3.x. I cannot imagine someone running
|
||||
# CMake on those ancient systems
|
||||
CMAKE_SYSTEM_NAME STREQUAL "FreeBSD" OR
|
||||
|
||||
CMAKE_SYSTEM_NAME STREQUAL "Haiku")
|
||||
|
||||
math(EXPR CMAKESONAME "${VERSIONCHANGE} - ${VERSIONDEL}")
|
||||
set(CMAKEVERSION "${CMAKESONAME}.${VERSIONDEL}.${VERSIONADD}")
|
||||
|
||||
set_target_properties(${LIB_NAME} PROPERTIES
|
||||
VERSION ${CMAKEVERSION}
|
||||
SOVERSION ${CMAKESONAME}
|
||||
)
|
||||
|
||||
endif()
|
||||
|
||||
|
||||
if(HIDES_CURL_PRIVATE_SYMBOLS)
|
||||
set_property(TARGET ${LIB_NAME} APPEND PROPERTY COMPILE_DEFINITIONS "CURL_HIDDEN_SYMBOLS")
|
||||
set_property(TARGET ${LIB_NAME} APPEND PROPERTY COMPILE_FLAGS ${CURL_CFLAG_SYMBOLS_HIDE})
|
||||
|
@ -121,27 +144,38 @@ endif()
|
|||
set_target_properties(${LIB_NAME} PROPERTIES PREFIX "")
|
||||
set_target_properties(${LIB_NAME} PROPERTIES IMPORT_PREFIX "")
|
||||
|
||||
if(CURL_HAS_LTO)
|
||||
set_target_properties(${LIB_NAME} PROPERTIES
|
||||
INTERPROCEDURAL_OPTIMIZATION_RELEASE TRUE
|
||||
INTERPROCEDURAL_OPTIMIZATION_RELWITHDEBINFO TRUE)
|
||||
endif()
|
||||
|
||||
if(WIN32)
|
||||
if(BUILD_SHARED_LIBS)
|
||||
# Add "_imp" as a suffix before the extension to avoid conflicting with the statically linked "libcurl.lib"
|
||||
set_target_properties(${LIB_NAME} PROPERTIES IMPORT_SUFFIX "_imp.lib")
|
||||
if(MSVC)
|
||||
# Add "_imp" as a suffix before the extension to avoid conflicting with
|
||||
# the statically linked "libcurl.lib"
|
||||
set_target_properties(${LIB_NAME} PROPERTIES IMPORT_SUFFIX "_imp.lib")
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
target_include_directories(${LIB_NAME} INTERFACE
|
||||
$<INSTALL_INTERFACE:include>
|
||||
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>
|
||||
$<BUILD_INTERFACE:${CURL_SOURCE_DIR}/include>)
|
||||
|
||||
install(TARGETS ${LIB_NAME}
|
||||
EXPORT ${TARGETS_EXPORT_NAME}
|
||||
ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
|
||||
)
|
||||
if(CURL_ENABLE_EXPORT_TARGET)
|
||||
install(TARGETS ${LIB_NAME}
|
||||
EXPORT ${TARGETS_EXPORT_NAME}
|
||||
ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
|
||||
)
|
||||
|
||||
export(TARGETS ${LIB_NAME}
|
||||
APPEND FILE ${PROJECT_BINARY_DIR}/libcurl-target.cmake
|
||||
NAMESPACE CURL::
|
||||
)
|
||||
export(TARGETS ${LIB_NAME}
|
||||
FILE ${PROJECT_BINARY_DIR}/libcurl-target.cmake
|
||||
NAMESPACE ${PROJECT_NAME}::
|
||||
)
|
||||
endif()
|
||||
|
||||
endif()
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
# | (__| |_| | _ <| |___
|
||||
# \___|\___/|_| \_\_____|
|
||||
#
|
||||
# Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
# Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
#
|
||||
# This software is licensed as described in the file COPYING, which
|
||||
# you should have received as part of this distribution. The terms
|
||||
# are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
# are also available at https://curl.se/docs/copyright.html.
|
||||
#
|
||||
# You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
# copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,67 +18,344 @@
|
|||
# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
# KIND, either express or implied.
|
||||
#
|
||||
# SPDX-License-Identifier: curl
|
||||
#
|
||||
###########################################################################
|
||||
|
||||
LIB_VAUTH_CFILES = vauth/vauth.c vauth/cleartext.c vauth/cram.c \
|
||||
vauth/digest.c vauth/digest_sspi.c vauth/krb5_gssapi.c \
|
||||
vauth/krb5_sspi.c vauth/ntlm.c vauth/ntlm_sspi.c vauth/oauth2.c \
|
||||
vauth/spnego_gssapi.c vauth/spnego_sspi.c
|
||||
LIB_VAUTH_CFILES = \
|
||||
vauth/cleartext.c \
|
||||
vauth/cram.c \
|
||||
vauth/digest.c \
|
||||
vauth/digest_sspi.c \
|
||||
vauth/gsasl.c \
|
||||
vauth/krb5_gssapi.c \
|
||||
vauth/krb5_sspi.c \
|
||||
vauth/ntlm.c \
|
||||
vauth/ntlm_sspi.c \
|
||||
vauth/oauth2.c \
|
||||
vauth/spnego_gssapi.c \
|
||||
vauth/spnego_sspi.c \
|
||||
vauth/vauth.c
|
||||
|
||||
LIB_VAUTH_HFILES = vauth/vauth.h vauth/digest.h vauth/ntlm.h
|
||||
LIB_VAUTH_HFILES = \
|
||||
vauth/digest.h \
|
||||
vauth/ntlm.h \
|
||||
vauth/vauth.h
|
||||
|
||||
LIB_VTLS_CFILES = vtls/openssl.c vtls/gtls.c vtls/vtls.c vtls/nss.c \
|
||||
vtls/polarssl.c vtls/polarssl_threadlock.c \
|
||||
vtls/cyassl.c vtls/schannel.c vtls/schannel_verify.c \
|
||||
vtls/sectransp.c vtls/gskit.c vtls/mbedtls.c vtls/mesalink.c
|
||||
LIB_VTLS_CFILES = \
|
||||
vtls/bearssl.c \
|
||||
vtls/gskit.c \
|
||||
vtls/gtls.c \
|
||||
vtls/hostcheck.c \
|
||||
vtls/keylog.c \
|
||||
vtls/mbedtls.c \
|
||||
vtls/mbedtls_threadlock.c \
|
||||
vtls/nss.c \
|
||||
vtls/openssl.c \
|
||||
vtls/rustls.c \
|
||||
vtls/schannel.c \
|
||||
vtls/schannel_verify.c \
|
||||
vtls/sectransp.c \
|
||||
vtls/vtls.c \
|
||||
vtls/wolfssl.c \
|
||||
vtls/x509asn1.c
|
||||
|
||||
LIB_VTLS_HFILES = vtls/openssl.h vtls/vtls.h vtls/gtls.h \
|
||||
vtls/nssg.h vtls/polarssl.h vtls/polarssl_threadlock.h \
|
||||
vtls/cyassl.h vtls/schannel.h vtls/sectransp.h vtls/gskit.h \
|
||||
vtls/mbedtls.h vtls/mesalink.h
|
||||
LIB_VTLS_HFILES = \
|
||||
vtls/bearssl.h \
|
||||
vtls/gskit.h \
|
||||
vtls/gtls.h \
|
||||
vtls/hostcheck.h \
|
||||
vtls/keylog.h \
|
||||
vtls/mbedtls.h \
|
||||
vtls/mbedtls_threadlock.h \
|
||||
vtls/nssg.h \
|
||||
vtls/openssl.h \
|
||||
vtls/rustls.h \
|
||||
vtls/schannel.h \
|
||||
vtls/sectransp.h \
|
||||
vtls/vtls.h \
|
||||
vtls/vtls_int.h \
|
||||
vtls/wolfssl.h \
|
||||
vtls/x509asn1.h
|
||||
|
||||
LIB_CFILES = file.c timeval.c base64.c hostip.c progress.c formdata.c \
|
||||
cookie.c http.c sendf.c ftp.c url.c dict.c if2ip.c speedcheck.c \
|
||||
ldap.c version.c getenv.c escape.c mprintf.c telnet.c netrc.c \
|
||||
getinfo.c transfer.c strcase.c easy.c security.c curl_fnmatch.c \
|
||||
fileinfo.c ftplistparser.c wildcard.c krb5.c memdebug.c http_chunks.c \
|
||||
strtok.c connect.c llist.c hash.c multi.c content_encoding.c share.c \
|
||||
http_digest.c md4.c md5.c http_negotiate.c inet_pton.c strtoofft.c \
|
||||
strerror.c amigaos.c hostasyn.c hostip4.c hostip6.c hostsyn.c \
|
||||
inet_ntop.c parsedate.c select.c tftp.c splay.c strdup.c socks.c \
|
||||
ssh.c ssh-libssh.c curl_addrinfo.c socks_gssapi.c socks_sspi.c \
|
||||
curl_sspi.c slist.c nonblock.c curl_memrchr.c imap.c pop3.c smtp.c \
|
||||
pingpong.c rtsp.c curl_threads.c warnless.c hmac.c curl_rtmp.c \
|
||||
openldap.c curl_gethostname.c gopher.c idn_win32.c \
|
||||
http_proxy.c non-ascii.c asyn-ares.c asyn-thread.c curl_gssapi.c \
|
||||
http_ntlm.c curl_ntlm_wb.c curl_ntlm_core.c curl_sasl.c rand.c \
|
||||
curl_multibyte.c hostcheck.c conncache.c dotdot.c \
|
||||
x509asn1.c http2.c smb.c curl_endian.c curl_des.c system_win32.c \
|
||||
mime.c sha256.c setopt.c curl_path.c curl_ctype.c curl_range.c psl.c \
|
||||
doh.c urlapi.c curl_get_line.c altsvc.c
|
||||
LIB_VQUIC_CFILES = \
|
||||
vquic/curl_msh3.c \
|
||||
vquic/curl_ngtcp2.c \
|
||||
vquic/curl_quiche.c \
|
||||
vquic/vquic.c
|
||||
|
||||
LIB_HFILES = arpa_telnet.h netrc.h file.h timeval.h hostip.h progress.h \
|
||||
formdata.h cookie.h http.h sendf.h ftp.h url.h dict.h if2ip.h \
|
||||
speedcheck.h urldata.h curl_ldap.h escape.h telnet.h getinfo.h \
|
||||
strcase.h curl_sec.h memdebug.h http_chunks.h curl_fnmatch.h \
|
||||
wildcard.h fileinfo.h ftplistparser.h strtok.h connect.h llist.h \
|
||||
hash.h content_encoding.h share.h curl_md4.h curl_md5.h http_digest.h \
|
||||
http_negotiate.h inet_pton.h amigaos.h strtoofft.h strerror.h \
|
||||
inet_ntop.h curlx.h curl_memory.h curl_setup.h transfer.h select.h \
|
||||
easyif.h multiif.h parsedate.h tftp.h sockaddr.h splay.h strdup.h \
|
||||
socks.h ssh.h curl_base64.h curl_addrinfo.h curl_sspi.h \
|
||||
slist.h nonblock.h curl_memrchr.h imap.h pop3.h smtp.h pingpong.h \
|
||||
rtsp.h curl_threads.h warnless.h curl_hmac.h curl_rtmp.h \
|
||||
curl_gethostname.h gopher.h http_proxy.h non-ascii.h asyn.h \
|
||||
http_ntlm.h curl_gssapi.h curl_ntlm_wb.h curl_ntlm_core.h \
|
||||
curl_sasl.h curl_multibyte.h hostcheck.h conncache.h \
|
||||
curl_setup_once.h multihandle.h setup-vms.h dotdot.h \
|
||||
x509asn1.h http2.h sigpipe.h smb.h curl_endian.h curl_des.h \
|
||||
curl_printf.h system_win32.h rand.h mime.h curl_sha256.h setopt.h \
|
||||
curl_path.h curl_ctype.h curl_range.h psl.h doh.h urlapi-int.h \
|
||||
curl_get_line.h altsvc.h
|
||||
LIB_VQUIC_HFILES = \
|
||||
vquic/curl_msh3.h \
|
||||
vquic/curl_ngtcp2.h \
|
||||
vquic/curl_quiche.h \
|
||||
vquic/vquic.h \
|
||||
vquic/vquic_int.h
|
||||
|
||||
LIB_VSSH_CFILES = \
|
||||
vssh/libssh.c \
|
||||
vssh/libssh2.c \
|
||||
vssh/wolfssh.c
|
||||
|
||||
LIB_VSSH_HFILES = \
|
||||
vssh/ssh.h
|
||||
|
||||
LIB_CFILES = \
|
||||
altsvc.c \
|
||||
amigaos.c \
|
||||
asyn-ares.c \
|
||||
asyn-thread.c \
|
||||
base64.c \
|
||||
bufref.c \
|
||||
c-hyper.c \
|
||||
cf-https-connect.c \
|
||||
cf-socket.c \
|
||||
cfilters.c \
|
||||
conncache.c \
|
||||
connect.c \
|
||||
content_encoding.c \
|
||||
cookie.c \
|
||||
curl_addrinfo.c \
|
||||
curl_des.c \
|
||||
curl_endian.c \
|
||||
curl_fnmatch.c \
|
||||
curl_get_line.c \
|
||||
curl_gethostname.c \
|
||||
curl_gssapi.c \
|
||||
curl_log.c \
|
||||
curl_memrchr.c \
|
||||
curl_multibyte.c \
|
||||
curl_ntlm_core.c \
|
||||
curl_ntlm_wb.c \
|
||||
curl_path.c \
|
||||
curl_range.c \
|
||||
curl_rtmp.c \
|
||||
curl_sasl.c \
|
||||
curl_sspi.c \
|
||||
curl_threads.c \
|
||||
dict.c \
|
||||
doh.c \
|
||||
dynbuf.c \
|
||||
easy.c \
|
||||
easygetopt.c \
|
||||
easyoptions.c \
|
||||
escape.c \
|
||||
file.c \
|
||||
fileinfo.c \
|
||||
fopen.c \
|
||||
formdata.c \
|
||||
ftp.c \
|
||||
ftplistparser.c \
|
||||
getenv.c \
|
||||
getinfo.c \
|
||||
gopher.c \
|
||||
h2h3.c \
|
||||
hash.c \
|
||||
headers.c \
|
||||
hmac.c \
|
||||
hostasyn.c \
|
||||
hostip.c \
|
||||
hostip4.c \
|
||||
hostip6.c \
|
||||
hostsyn.c \
|
||||
hsts.c \
|
||||
http.c \
|
||||
http2.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 \
|
||||
inet_ntop.c \
|
||||
inet_pton.c \
|
||||
krb5.c \
|
||||
ldap.c \
|
||||
llist.c \
|
||||
md4.c \
|
||||
md5.c \
|
||||
memdebug.c \
|
||||
mime.c \
|
||||
mprintf.c \
|
||||
mqtt.c \
|
||||
multi.c \
|
||||
netrc.c \
|
||||
nonblock.c \
|
||||
noproxy.c \
|
||||
openldap.c \
|
||||
parsedate.c \
|
||||
pingpong.c \
|
||||
pop3.c \
|
||||
progress.c \
|
||||
psl.c \
|
||||
rand.c \
|
||||
rename.c \
|
||||
rtsp.c \
|
||||
select.c \
|
||||
sendf.c \
|
||||
setopt.c \
|
||||
sha256.c \
|
||||
share.c \
|
||||
slist.c \
|
||||
smb.c \
|
||||
smtp.c \
|
||||
socketpair.c \
|
||||
socks.c \
|
||||
socks_gssapi.c \
|
||||
socks_sspi.c \
|
||||
speedcheck.c \
|
||||
splay.c \
|
||||
strcase.c \
|
||||
strdup.c \
|
||||
strerror.c \
|
||||
strtok.c \
|
||||
strtoofft.c \
|
||||
system_win32.c \
|
||||
telnet.c \
|
||||
tftp.c \
|
||||
timediff.c \
|
||||
timeval.c \
|
||||
transfer.c \
|
||||
url.c \
|
||||
urlapi.c \
|
||||
version.c \
|
||||
version_win32.c \
|
||||
warnless.c \
|
||||
ws.c
|
||||
|
||||
LIB_HFILES = \
|
||||
altsvc.h \
|
||||
amigaos.h \
|
||||
arpa_telnet.h \
|
||||
asyn.h \
|
||||
bufref.h \
|
||||
c-hyper.h \
|
||||
cf-https-connect.h \
|
||||
cf-socket.h \
|
||||
cfilters.h \
|
||||
conncache.h \
|
||||
connect.h \
|
||||
content_encoding.h \
|
||||
cookie.h \
|
||||
curl_addrinfo.h \
|
||||
curl_base64.h \
|
||||
curl_ctype.h \
|
||||
curl_des.h \
|
||||
curl_endian.h \
|
||||
curl_fnmatch.h \
|
||||
curl_get_line.h \
|
||||
curl_gethostname.h \
|
||||
curl_gssapi.h \
|
||||
curl_hmac.h \
|
||||
curl_krb5.h \
|
||||
curl_ldap.h \
|
||||
curl_log.h \
|
||||
curl_md4.h \
|
||||
curl_md5.h \
|
||||
curl_memory.h \
|
||||
curl_memrchr.h \
|
||||
curl_multibyte.h \
|
||||
curl_ntlm_core.h \
|
||||
curl_ntlm_wb.h \
|
||||
curl_path.h \
|
||||
curl_printf.h \
|
||||
curl_range.h \
|
||||
curl_rtmp.h \
|
||||
curl_sasl.h \
|
||||
curl_setup.h \
|
||||
curl_setup_once.h \
|
||||
curl_sha256.h \
|
||||
curl_sspi.h \
|
||||
curl_threads.h \
|
||||
curlx.h \
|
||||
dict.h \
|
||||
doh.h \
|
||||
dynbuf.h \
|
||||
easy_lock.h \
|
||||
easyif.h \
|
||||
easyoptions.h \
|
||||
escape.h \
|
||||
file.h \
|
||||
fileinfo.h \
|
||||
fopen.h \
|
||||
formdata.h \
|
||||
functypes.h \
|
||||
ftp.h \
|
||||
ftplistparser.h \
|
||||
getinfo.h \
|
||||
gopher.h \
|
||||
h2h3.h \
|
||||
hash.h \
|
||||
headers.h \
|
||||
hostip.h \
|
||||
hsts.h \
|
||||
http.h \
|
||||
http2.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 \
|
||||
inet_ntop.h \
|
||||
inet_pton.h \
|
||||
llist.h \
|
||||
memdebug.h \
|
||||
mime.h \
|
||||
mqtt.h \
|
||||
multihandle.h \
|
||||
multiif.h \
|
||||
netrc.h \
|
||||
nonblock.h \
|
||||
noproxy.h \
|
||||
parsedate.h \
|
||||
pingpong.h \
|
||||
pop3.h \
|
||||
progress.h \
|
||||
psl.h \
|
||||
rand.h \
|
||||
rename.h \
|
||||
rtsp.h \
|
||||
select.h \
|
||||
sendf.h \
|
||||
setopt.h \
|
||||
setup-vms.h \
|
||||
share.h \
|
||||
sigpipe.h \
|
||||
slist.h \
|
||||
smb.h \
|
||||
smtp.h \
|
||||
sockaddr.h \
|
||||
socketpair.h \
|
||||
socks.h \
|
||||
speedcheck.h \
|
||||
splay.h \
|
||||
strcase.h \
|
||||
strdup.h \
|
||||
strerror.h \
|
||||
strtok.h \
|
||||
strtoofft.h \
|
||||
system_win32.h \
|
||||
telnet.h \
|
||||
tftp.h \
|
||||
timediff.h \
|
||||
timeval.h \
|
||||
transfer.h \
|
||||
url.h \
|
||||
urlapi-int.h \
|
||||
urldata.h \
|
||||
version_win32.h \
|
||||
warnless.h \
|
||||
ws.h
|
||||
|
||||
LIB_RCFILES = libcurl.rc
|
||||
|
||||
CSOURCES = $(LIB_CFILES) $(LIB_VAUTH_CFILES) $(LIB_VTLS_CFILES)
|
||||
HHEADERS = $(LIB_HFILES) $(LIB_VAUTH_HFILES) $(LIB_VTLS_HFILES)
|
||||
CSOURCES = $(LIB_CFILES) $(LIB_VAUTH_CFILES) $(LIB_VTLS_CFILES) \
|
||||
$(LIB_VQUIC_CFILES) $(LIB_VSSH_CFILES)
|
||||
HHEADERS = $(LIB_HFILES) $(LIB_VAUTH_HFILES) $(LIB_VTLS_HFILES) \
|
||||
$(LIB_VQUIC_HFILES) $(LIB_VSSH_HFILES)
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,14 +18,16 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
/*
|
||||
* The Alt-Svc: header is defined in RFC 7838:
|
||||
* https://tools.ietf.org/html/rfc7838
|
||||
* https://datatracker.ietf.org/doc/html/rfc7838
|
||||
*/
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if !defined(CURL_DISABLE_HTTP) && defined(USE_ALTSVC)
|
||||
#if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_ALTSVC)
|
||||
#include <curl/curl.h>
|
||||
#include "urldata.h"
|
||||
#include "altsvc.h"
|
||||
|
@ -34,6 +36,8 @@
|
|||
#include "parsedate.h"
|
||||
#include "sendf.h"
|
||||
#include "warnless.h"
|
||||
#include "fopen.h"
|
||||
#include "rename.h"
|
||||
|
||||
/* The last 3 #include files should be in this order */
|
||||
#include "curl_printf.h"
|
||||
|
@ -48,15 +52,15 @@
|
|||
#define MAX_ALTSVC_ALPNLENSTR "10"
|
||||
#define MAX_ALTSVC_ALPNLEN 10
|
||||
|
||||
#define H3VERSION "h3"
|
||||
|
||||
static enum alpnid alpn2alpnid(char *name)
|
||||
{
|
||||
if(strcasecompare(name, "h1"))
|
||||
return ALPN_h1;
|
||||
if(strcasecompare(name, "h2"))
|
||||
return ALPN_h2;
|
||||
if(strcasecompare(name, "h2c"))
|
||||
return ALPN_h2c;
|
||||
if(strcasecompare(name, "h3"))
|
||||
if(strcasecompare(name, H3VERSION))
|
||||
return ALPN_h3;
|
||||
return ALPN_none; /* unknown, probably rubbish input */
|
||||
}
|
||||
|
@ -69,10 +73,8 @@ const char *Curl_alpnid2str(enum alpnid id)
|
|||
return "h1";
|
||||
case ALPN_h2:
|
||||
return "h2";
|
||||
case ALPN_h2c:
|
||||
return "h2c";
|
||||
case ALPN_h3:
|
||||
return "h3";
|
||||
return H3VERSION;
|
||||
default:
|
||||
return ""; /* bad */
|
||||
}
|
||||
|
@ -81,8 +83,8 @@ const char *Curl_alpnid2str(enum alpnid id)
|
|||
|
||||
static void altsvc_free(struct altsvc *as)
|
||||
{
|
||||
free(as->srchost);
|
||||
free(as->dsthost);
|
||||
free(as->src.host);
|
||||
free(as->dst.host);
|
||||
free(as);
|
||||
}
|
||||
|
||||
|
@ -94,20 +96,25 @@ static struct altsvc *altsvc_createid(const char *srchost,
|
|||
unsigned int dstport)
|
||||
{
|
||||
struct altsvc *as = calloc(sizeof(struct altsvc), 1);
|
||||
size_t hlen;
|
||||
if(!as)
|
||||
return NULL;
|
||||
|
||||
as->srchost = strdup(srchost);
|
||||
if(!as->srchost)
|
||||
hlen = strlen(srchost);
|
||||
DEBUGASSERT(hlen);
|
||||
as->src.host = strdup(srchost);
|
||||
if(!as->src.host)
|
||||
goto error;
|
||||
as->dsthost = strdup(dsthost);
|
||||
if(!as->dsthost)
|
||||
if(hlen && (srchost[hlen - 1] == '.'))
|
||||
/* strip off trailing any dot */
|
||||
as->src.host[--hlen] = 0;
|
||||
as->dst.host = strdup(dsthost);
|
||||
if(!as->dst.host)
|
||||
goto error;
|
||||
|
||||
as->srcalpnid = srcalpnid;
|
||||
as->dstalpnid = dstalpnid;
|
||||
as->srcport = curlx_ultous(srcport);
|
||||
as->dstport = curlx_ultous(dstport);
|
||||
as->src.alpnid = srcalpnid;
|
||||
as->dst.alpnid = dstalpnid;
|
||||
as->src.port = curlx_ultous(srcport);
|
||||
as->dst.port = curlx_ultous(dstport);
|
||||
|
||||
return as;
|
||||
error:
|
||||
|
@ -156,14 +163,13 @@ static CURLcode altsvc_add(struct altsvcinfo *asi, char *line)
|
|||
date, &persist, &prio);
|
||||
if(9 == rc) {
|
||||
struct altsvc *as;
|
||||
time_t expires = curl_getdate(date, NULL);
|
||||
time_t expires = Curl_getdate_capped(date);
|
||||
as = altsvc_create(srchost, dsthost, srcalpn, dstalpn, srcport, dstport);
|
||||
if(as) {
|
||||
as->expires = expires;
|
||||
as->prio = prio;
|
||||
as->persist = persist ? 1 : 0;
|
||||
Curl_llist_insert_next(&asi->list, asi->list.tail, as, &as->node);
|
||||
asi->num++; /* one more entry */
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -172,10 +178,9 @@ static CURLcode altsvc_add(struct altsvcinfo *asi, char *line)
|
|||
|
||||
/*
|
||||
* Load alt-svc entries from the given file. The text based line-oriented file
|
||||
* format is documented here:
|
||||
* https://github.com/curl/curl/wiki/QUIC-implementation
|
||||
* format is documented here: https://curl.se/docs/alt-svc.html
|
||||
*
|
||||
* This function only returns error on major problems that prevents alt-svc
|
||||
* This function only returns error on major problems that prevent alt-svc
|
||||
* handling to work completely. It will ignore individual syntactical errors
|
||||
* etc.
|
||||
*/
|
||||
|
@ -183,7 +188,16 @@ static CURLcode altsvc_load(struct altsvcinfo *asi, const char *file)
|
|||
{
|
||||
CURLcode result = CURLE_OK;
|
||||
char *line = NULL;
|
||||
FILE *fp = fopen(file, FOPEN_READTEXT);
|
||||
FILE *fp;
|
||||
|
||||
/* we need a private copy of the file name so that the altsvc cache file
|
||||
name survives an easy handle reset */
|
||||
free(asi->filename);
|
||||
asi->filename = strdup(file);
|
||||
if(!asi->filename)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
||||
fp = fopen(file, FOPEN_READTEXT);
|
||||
if(fp) {
|
||||
line = malloc(MAX_ALTSVC_LINE);
|
||||
if(!line)
|
||||
|
@ -204,6 +218,7 @@ static CURLcode altsvc_load(struct altsvcinfo *asi, const char *file)
|
|||
return result;
|
||||
|
||||
fail:
|
||||
Curl_safefree(asi->filename);
|
||||
free(line);
|
||||
fclose(fp);
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
@ -226,8 +241,8 @@ static CURLcode altsvc_out(struct altsvc *as, FILE *fp)
|
|||
"\"%d%02d%02d "
|
||||
"%02d:%02d:%02d\" "
|
||||
"%u %d\n",
|
||||
Curl_alpnid2str(as->srcalpnid), as->srchost, as->srcport,
|
||||
Curl_alpnid2str(as->dstalpnid), as->dsthost, as->dstport,
|
||||
Curl_alpnid2str(as->src.alpnid), as->src.host, as->src.port,
|
||||
Curl_alpnid2str(as->dst.alpnid), as->dst.host, as->dst.port,
|
||||
stamp.tm_year + 1900, stamp.tm_mon + 1, stamp.tm_mday,
|
||||
stamp.tm_hour, stamp.tm_min, stamp.tm_sec,
|
||||
as->persist, as->prio);
|
||||
|
@ -249,10 +264,10 @@ struct altsvcinfo *Curl_altsvc_init(void)
|
|||
|
||||
/* set default behavior */
|
||||
asi->flags = CURLALTSVC_H1
|
||||
#ifdef USE_NGHTTP2
|
||||
#ifdef USE_HTTP2
|
||||
| CURLALTSVC_H2
|
||||
#endif
|
||||
#ifdef USE_HTTP3
|
||||
#ifdef ENABLE_QUIC
|
||||
| CURLALTSVC_H3
|
||||
#endif
|
||||
;
|
||||
|
@ -287,51 +302,67 @@ CURLcode Curl_altsvc_ctrl(struct altsvcinfo *asi, const long ctrl)
|
|||
* Curl_altsvc_cleanup() frees an altsvc cache instance and all associated
|
||||
* resources.
|
||||
*/
|
||||
void Curl_altsvc_cleanup(struct altsvcinfo *altsvc)
|
||||
void Curl_altsvc_cleanup(struct altsvcinfo **altsvcp)
|
||||
{
|
||||
struct curl_llist_element *e;
|
||||
struct curl_llist_element *n;
|
||||
if(altsvc) {
|
||||
struct Curl_llist_element *e;
|
||||
struct Curl_llist_element *n;
|
||||
if(*altsvcp) {
|
||||
struct altsvcinfo *altsvc = *altsvcp;
|
||||
for(e = altsvc->list.head; e; e = n) {
|
||||
struct altsvc *as = e->ptr;
|
||||
n = e->next;
|
||||
altsvc_free(as);
|
||||
}
|
||||
free(altsvc->filename);
|
||||
free(altsvc);
|
||||
*altsvcp = NULL; /* clear the pointer */
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Curl_altsvc_save() writes the altsvc cache to a file.
|
||||
*/
|
||||
CURLcode Curl_altsvc_save(struct altsvcinfo *altsvc, const char *file)
|
||||
CURLcode Curl_altsvc_save(struct Curl_easy *data,
|
||||
struct altsvcinfo *altsvc, const char *file)
|
||||
{
|
||||
struct curl_llist_element *e;
|
||||
struct curl_llist_element *n;
|
||||
struct Curl_llist_element *e;
|
||||
struct Curl_llist_element *n;
|
||||
CURLcode result = CURLE_OK;
|
||||
FILE *out;
|
||||
char *tempstore = NULL;
|
||||
|
||||
if(!altsvc)
|
||||
/* no cache activated */
|
||||
return CURLE_OK;
|
||||
|
||||
if((altsvc->flags & CURLALTSVC_READONLYFILE) || !file[0])
|
||||
/* marked as read-only or zero length file name */
|
||||
/* if not new name is given, use the one we stored from the load */
|
||||
if(!file && altsvc->filename)
|
||||
file = altsvc->filename;
|
||||
|
||||
if((altsvc->flags & CURLALTSVC_READONLYFILE) || !file || !file[0])
|
||||
/* marked as read-only, no file or zero length file name */
|
||||
return CURLE_OK;
|
||||
out = fopen(file, FOPEN_WRITETEXT);
|
||||
if(!out)
|
||||
return CURLE_WRITE_ERROR;
|
||||
fputs("# Your alt-svc cache. https://curl.haxx.se/docs/alt-svc.html\n"
|
||||
"# This file was generated by libcurl! Edit at your own risk.\n",
|
||||
out);
|
||||
for(e = altsvc->list.head; e; e = n) {
|
||||
struct altsvc *as = e->ptr;
|
||||
n = e->next;
|
||||
result = altsvc_out(as, out);
|
||||
if(result)
|
||||
break;
|
||||
|
||||
result = Curl_fopen(data, file, &out, &tempstore);
|
||||
if(!result) {
|
||||
fputs("# Your alt-svc cache. https://curl.se/docs/alt-svc.html\n"
|
||||
"# This file was generated by libcurl! Edit at your own risk.\n",
|
||||
out);
|
||||
for(e = altsvc->list.head; e; e = n) {
|
||||
struct altsvc *as = e->ptr;
|
||||
n = e->next;
|
||||
result = altsvc_out(as, out);
|
||||
if(result)
|
||||
break;
|
||||
}
|
||||
fclose(out);
|
||||
if(!result && tempstore && Curl_rename(tempstore, file))
|
||||
result = CURLE_WRITE_ERROR;
|
||||
|
||||
if(result && tempstore)
|
||||
unlink(tempstore);
|
||||
}
|
||||
fclose(out);
|
||||
free(tempstore);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -343,34 +374,49 @@ static CURLcode getalnum(const char **ptr, char *alpnbuf, size_t buflen)
|
|||
while(*p && ISBLANK(*p))
|
||||
p++;
|
||||
protop = p;
|
||||
while(*p && ISALNUM(*p))
|
||||
while(*p && !ISBLANK(*p) && (*p != ';') && (*p != '='))
|
||||
p++;
|
||||
len = p - protop;
|
||||
*ptr = p;
|
||||
|
||||
if(!len || (len >= buflen))
|
||||
return CURLE_BAD_FUNCTION_ARGUMENT;
|
||||
memcpy(alpnbuf, protop, len);
|
||||
alpnbuf[len] = 0;
|
||||
*ptr = p;
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
/* hostcompare() returns true if 'host' matches 'check'. The first host
|
||||
* argument may have a trailing dot present that will be ignored.
|
||||
*/
|
||||
static bool hostcompare(const char *host, const char *check)
|
||||
{
|
||||
size_t hlen = strlen(host);
|
||||
size_t clen = strlen(check);
|
||||
|
||||
if(hlen && (host[hlen - 1] == '.'))
|
||||
hlen--;
|
||||
if(hlen != clen)
|
||||
/* they can't match if they have different lengths */
|
||||
return FALSE;
|
||||
return strncasecompare(host, check, hlen);
|
||||
}
|
||||
|
||||
/* altsvc_flush() removes all alternatives for this source origin from the
|
||||
list */
|
||||
static void altsvc_flush(struct altsvcinfo *asi, enum alpnid srcalpnid,
|
||||
const char *srchost, unsigned short srcport)
|
||||
{
|
||||
struct curl_llist_element *e;
|
||||
struct curl_llist_element *n;
|
||||
struct Curl_llist_element *e;
|
||||
struct Curl_llist_element *n;
|
||||
for(e = asi->list.head; e; e = n) {
|
||||
struct altsvc *as = e->ptr;
|
||||
n = e->next;
|
||||
if((srcalpnid == as->srcalpnid) &&
|
||||
(srcport == as->srcport) &&
|
||||
strcasecompare(srchost, as->srchost)) {
|
||||
if((srcalpnid == as->src.alpnid) &&
|
||||
(srcport == as->src.port) &&
|
||||
hostcompare(srchost, as->src.host)) {
|
||||
Curl_llist_remove(&asi->list, e, NULL);
|
||||
altsvc_free(as);
|
||||
asi->num--;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -391,12 +437,18 @@ static time_t debugtime(void *unused)
|
|||
#define time(x) debugtime(x)
|
||||
#endif
|
||||
|
||||
#define ISNEWLINE(x) (((x) == '\n') || (x) == '\r')
|
||||
|
||||
/*
|
||||
* Curl_altsvc_parse() takes an incoming alt-svc response header and stores
|
||||
* the data correctly in the cache.
|
||||
*
|
||||
* 'value' points to the header *value*. That's contents to the right of the
|
||||
* header name.
|
||||
*
|
||||
* Currently this function rejects invalid data without returning an error.
|
||||
* Invalid host name, port number will result in the specific alternative
|
||||
* being rejected. Unknown protocols are skipped.
|
||||
*/
|
||||
CURLcode Curl_altsvc_parse(struct Curl_easy *data,
|
||||
struct altsvcinfo *asi, const char *value,
|
||||
|
@ -405,69 +457,44 @@ CURLcode Curl_altsvc_parse(struct Curl_easy *data,
|
|||
{
|
||||
const char *p = value;
|
||||
size_t len;
|
||||
enum alpnid dstalpnid = srcalpnid; /* the same by default */
|
||||
char namebuf[MAX_ALTSVC_HOSTLEN] = "";
|
||||
char alpnbuf[MAX_ALTSVC_ALPNLEN] = "";
|
||||
struct altsvc *as;
|
||||
unsigned short dstport = srcport; /* the same by default */
|
||||
const char *semip;
|
||||
time_t maxage = 24 * 3600; /* default is 24 hours */
|
||||
bool persist = FALSE;
|
||||
CURLcode result = getalnum(&p, alpnbuf, sizeof(alpnbuf));
|
||||
if(result)
|
||||
return result;
|
||||
|
||||
DEBUGASSERT(asi);
|
||||
|
||||
/* Flush all cached alternatives for this source origin, if any */
|
||||
altsvc_flush(asi, srcalpnid, srchost, srcport);
|
||||
|
||||
/* "clear" is a magic keyword */
|
||||
if(strcasecompare(alpnbuf, "clear")) {
|
||||
size_t entries = 0;
|
||||
#ifdef CURL_DISABLE_VERBOSE_STRINGS
|
||||
(void)data;
|
||||
#endif
|
||||
if(result) {
|
||||
infof(data, "Excessive alt-svc header, ignoring.");
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
/* The 'ma' and 'persist' flags are annoyingly meant for all alternatives
|
||||
but are set after the list on the line. Scan for the semicolons and get
|
||||
those fields first! */
|
||||
semip = p;
|
||||
do {
|
||||
semip = strchr(semip, ';');
|
||||
if(semip) {
|
||||
char option[32];
|
||||
unsigned long num;
|
||||
char *end_ptr;
|
||||
semip++; /* pass the semicolon */
|
||||
result = getalnum(&semip, option, sizeof(option));
|
||||
if(result)
|
||||
break;
|
||||
while(*semip && ISBLANK(*semip))
|
||||
semip++;
|
||||
if(*semip != '=')
|
||||
continue;
|
||||
semip++;
|
||||
num = strtoul(semip, &end_ptr, 10);
|
||||
if(num < ULONG_MAX) {
|
||||
if(strcasecompare("ma", option))
|
||||
maxage = num;
|
||||
else if(strcasecompare("persist", option) && (num == 1))
|
||||
persist = TRUE;
|
||||
}
|
||||
semip = end_ptr;
|
||||
}
|
||||
} while(semip);
|
||||
DEBUGASSERT(asi);
|
||||
|
||||
/* "clear" is a magic keyword */
|
||||
if(strcasecompare(alpnbuf, "clear")) {
|
||||
/* Flush cached alternatives for this source origin */
|
||||
altsvc_flush(asi, srcalpnid, srchost, srcport);
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
do {
|
||||
if(*p == '=') {
|
||||
/* [protocol]="[host][:port]" */
|
||||
dstalpnid = alpn2alpnid(alpnbuf);
|
||||
if(!dstalpnid) {
|
||||
infof(data, "Unknown alt-svc protocol \"%s\", ignoring...\n", alpnbuf);
|
||||
return CURLE_OK;
|
||||
}
|
||||
enum alpnid dstalpnid = alpn2alpnid(alpnbuf); /* the same by default */
|
||||
p++;
|
||||
if(*p == '\"') {
|
||||
const char *dsthost;
|
||||
const char *dsthost = "";
|
||||
const char *value_ptr;
|
||||
char option[32];
|
||||
unsigned long num;
|
||||
char *end_ptr;
|
||||
bool quoted = FALSE;
|
||||
time_t maxage = 24 * 3600; /* default is 24 hours */
|
||||
bool persist = FALSE;
|
||||
bool valid = TRUE;
|
||||
p++;
|
||||
if(*p != ':') {
|
||||
/* host name starts here */
|
||||
|
@ -475,43 +502,109 @@ CURLcode Curl_altsvc_parse(struct Curl_easy *data,
|
|||
while(*p && (ISALNUM(*p) || (*p == '.') || (*p == '-')))
|
||||
p++;
|
||||
len = p - hostp;
|
||||
if(!len || (len >= MAX_ALTSVC_HOSTLEN))
|
||||
return CURLE_BAD_FUNCTION_ARGUMENT;
|
||||
memcpy(namebuf, hostp, len);
|
||||
namebuf[len] = 0;
|
||||
dsthost = namebuf;
|
||||
if(!len || (len >= MAX_ALTSVC_HOSTLEN)) {
|
||||
infof(data, "Excessive alt-svc host name, ignoring.");
|
||||
valid = FALSE;
|
||||
}
|
||||
else {
|
||||
memcpy(namebuf, hostp, len);
|
||||
namebuf[len] = 0;
|
||||
dsthost = namebuf;
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* no destination name, use source host */
|
||||
dsthost = srchost;
|
||||
}
|
||||
if(*p == ':') {
|
||||
/* a port number */
|
||||
char *end_ptr;
|
||||
unsigned long port = strtoul(++p, &end_ptr, 10);
|
||||
if(port > USHRT_MAX || end_ptr == p || *end_ptr != '\"') {
|
||||
infof(data, "Unknown alt-svc port number, ignoring...\n");
|
||||
return CURLE_OK;
|
||||
unsigned long port = 0;
|
||||
p++;
|
||||
if(ISDIGIT(*p))
|
||||
/* a port number */
|
||||
port = strtoul(p, &end_ptr, 10);
|
||||
else
|
||||
end_ptr = (char *)p; /* not left uninitialized */
|
||||
if(!port || port > USHRT_MAX || end_ptr == p || *end_ptr != '\"') {
|
||||
infof(data, "Unknown alt-svc port number, ignoring.");
|
||||
valid = FALSE;
|
||||
}
|
||||
else {
|
||||
dstport = curlx_ultous(port);
|
||||
p = end_ptr;
|
||||
}
|
||||
p = end_ptr;
|
||||
dstport = curlx_ultous(port);
|
||||
}
|
||||
if(*p++ != '\"')
|
||||
return CURLE_BAD_FUNCTION_ARGUMENT;
|
||||
as = altsvc_createid(srchost, dsthost,
|
||||
srcalpnid, dstalpnid,
|
||||
srcport, dstport);
|
||||
if(as) {
|
||||
/* The expires time also needs to take the Age: value (if any) into
|
||||
account. [See RFC 7838 section 3.1] */
|
||||
as->expires = maxage + time(NULL);
|
||||
as->persist = persist;
|
||||
Curl_llist_insert_next(&asi->list, asi->list.tail, as, &as->node);
|
||||
asi->num++; /* one more entry */
|
||||
infof(data, "Added alt-svc: %s:%d over %s\n", dsthost, dstport,
|
||||
Curl_alpnid2str(dstalpnid));
|
||||
break;
|
||||
/* Handle the optional 'ma' and 'persist' flags. Unknown flags
|
||||
are skipped. */
|
||||
for(;;) {
|
||||
while(ISBLANK(*p))
|
||||
p++;
|
||||
if(*p != ';')
|
||||
break;
|
||||
p++; /* pass the semicolon */
|
||||
if(!*p || ISNEWLINE(*p))
|
||||
break;
|
||||
result = getalnum(&p, option, sizeof(option));
|
||||
if(result) {
|
||||
/* skip option if name is too long */
|
||||
option[0] = '\0';
|
||||
}
|
||||
while(*p && ISBLANK(*p))
|
||||
p++;
|
||||
if(*p != '=')
|
||||
return CURLE_OK;
|
||||
p++;
|
||||
while(*p && ISBLANK(*p))
|
||||
p++;
|
||||
if(!*p)
|
||||
return CURLE_OK;
|
||||
if(*p == '\"') {
|
||||
/* quoted value */
|
||||
p++;
|
||||
quoted = TRUE;
|
||||
}
|
||||
value_ptr = p;
|
||||
if(quoted) {
|
||||
while(*p && *p != '\"')
|
||||
p++;
|
||||
if(!*p++)
|
||||
return CURLE_OK;
|
||||
}
|
||||
else {
|
||||
while(*p && !ISBLANK(*p) && *p!= ';' && *p != ',')
|
||||
p++;
|
||||
}
|
||||
num = strtoul(value_ptr, &end_ptr, 10);
|
||||
if((end_ptr != value_ptr) && (num < ULONG_MAX)) {
|
||||
if(strcasecompare("ma", option))
|
||||
maxage = num;
|
||||
else if(strcasecompare("persist", option) && (num == 1))
|
||||
persist = TRUE;
|
||||
}
|
||||
}
|
||||
if(dstalpnid && valid) {
|
||||
if(!entries++)
|
||||
/* Flush cached alternatives for this source origin, if any - when
|
||||
this is the first entry of the line. */
|
||||
altsvc_flush(asi, srcalpnid, srchost, srcport);
|
||||
|
||||
as = altsvc_createid(srchost, dsthost,
|
||||
srcalpnid, dstalpnid,
|
||||
srcport, dstport);
|
||||
if(as) {
|
||||
/* The expires time also needs to take the Age: value (if any) into
|
||||
account. [See RFC 7838 section 3.1] */
|
||||
as->expires = maxage + time(NULL);
|
||||
as->persist = persist;
|
||||
Curl_llist_insert_next(&asi->list, asi->list.tail, as, &as->node);
|
||||
infof(data, "Added alt-svc: %s:%d over %s", dsthost, dstport,
|
||||
Curl_alpnid2str(dstalpnid));
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
break;
|
||||
/* after the double quote there can be a comma if there's another
|
||||
string or a semicolon if no more */
|
||||
if(*p == ',') {
|
||||
|
@ -519,11 +612,11 @@ CURLcode Curl_altsvc_parse(struct Curl_easy *data,
|
|||
p++;
|
||||
result = getalnum(&p, alpnbuf, sizeof(alpnbuf));
|
||||
if(result)
|
||||
/* failed to parse, but since we already did at least one host we
|
||||
return OK */
|
||||
return CURLE_OK;
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
break;
|
||||
} while(*p && (*p != ';') && (*p != '\n') && (*p != '\r'));
|
||||
|
||||
return CURLE_OK;
|
||||
|
@ -535,35 +628,35 @@ CURLcode Curl_altsvc_parse(struct Curl_easy *data,
|
|||
bool Curl_altsvc_lookup(struct altsvcinfo *asi,
|
||||
enum alpnid srcalpnid, const char *srchost,
|
||||
int srcport,
|
||||
enum alpnid *dstalpnid, const char **dsthost,
|
||||
int *dstport)
|
||||
struct altsvc **dstentry,
|
||||
const int versions) /* one or more bits */
|
||||
{
|
||||
struct curl_llist_element *e;
|
||||
struct curl_llist_element *n;
|
||||
struct Curl_llist_element *e;
|
||||
struct Curl_llist_element *n;
|
||||
time_t now = time(NULL);
|
||||
DEBUGASSERT(asi);
|
||||
DEBUGASSERT(srchost);
|
||||
DEBUGASSERT(dsthost);
|
||||
DEBUGASSERT(dstentry);
|
||||
|
||||
for(e = asi->list.head; e; e = n) {
|
||||
struct altsvc *as = e->ptr;
|
||||
n = e->next;
|
||||
if(as->expires < now) {
|
||||
/* an expired entry, remove */
|
||||
Curl_llist_remove(&asi->list, e, NULL);
|
||||
altsvc_free(as);
|
||||
continue;
|
||||
}
|
||||
if((as->srcalpnid == srcalpnid) &&
|
||||
strcasecompare(as->srchost, srchost) &&
|
||||
as->srcport == srcport) {
|
||||
if((as->src.alpnid == srcalpnid) &&
|
||||
hostcompare(srchost, as->src.host) &&
|
||||
(as->src.port == srcport) &&
|
||||
(versions & as->dst.alpnid)) {
|
||||
/* match */
|
||||
*dstalpnid = as->dstalpnid;
|
||||
*dsthost = as->dsthost;
|
||||
*dstport = as->dstport;
|
||||
*dstentry = as;
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
#endif /* CURL_DISABLE_HTTP || USE_ALTSVC */
|
||||
#endif /* !CURL_DISABLE_HTTP && !CURL_DISABLE_ALTSVC */
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,47 +20,50 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if !defined(CURL_DISABLE_HTTP) && defined(USE_ALTSVC)
|
||||
#if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_ALTSVC)
|
||||
#include <curl/curl.h>
|
||||
#include "llist.h"
|
||||
|
||||
enum alpnid {
|
||||
ALPN_none,
|
||||
ALPN_h1,
|
||||
ALPN_h2,
|
||||
ALPN_h2c,
|
||||
ALPN_h3
|
||||
ALPN_none = 0,
|
||||
ALPN_h1 = CURLALTSVC_H1,
|
||||
ALPN_h2 = CURLALTSVC_H2,
|
||||
ALPN_h3 = CURLALTSVC_H3
|
||||
};
|
||||
|
||||
struct althost {
|
||||
char *host;
|
||||
unsigned short port;
|
||||
enum alpnid alpnid;
|
||||
};
|
||||
|
||||
struct altsvc {
|
||||
char *srchost;
|
||||
char *dsthost;
|
||||
unsigned short srcport;
|
||||
unsigned short dstport;
|
||||
enum alpnid srcalpnid;
|
||||
enum alpnid dstalpnid;
|
||||
struct althost src;
|
||||
struct althost dst;
|
||||
time_t expires;
|
||||
bool persist;
|
||||
int prio;
|
||||
struct curl_llist_element node;
|
||||
struct Curl_llist_element node;
|
||||
};
|
||||
|
||||
struct altsvcinfo {
|
||||
char *filename;
|
||||
struct curl_llist list; /* list of entries */
|
||||
size_t num; /* number of alt-svc entries */
|
||||
struct Curl_llist list; /* list of entries */
|
||||
long flags; /* the publicly set bitmask */
|
||||
};
|
||||
|
||||
const char *Curl_alpnid2str(enum alpnid id);
|
||||
struct altsvcinfo *Curl_altsvc_init(void);
|
||||
CURLcode Curl_altsvc_load(struct altsvcinfo *asi, const char *file);
|
||||
CURLcode Curl_altsvc_save(struct altsvcinfo *asi, const char *file);
|
||||
CURLcode Curl_altsvc_save(struct Curl_easy *data,
|
||||
struct altsvcinfo *asi, const char *file);
|
||||
CURLcode Curl_altsvc_ctrl(struct altsvcinfo *asi, const long ctrl);
|
||||
void Curl_altsvc_cleanup(struct altsvcinfo *altsvc);
|
||||
void Curl_altsvc_cleanup(struct altsvcinfo **altsvc);
|
||||
CURLcode Curl_altsvc_parse(struct Curl_easy *data,
|
||||
struct altsvcinfo *altsvc, const char *value,
|
||||
enum alpnid srcalpn, const char *srchost,
|
||||
|
@ -68,10 +71,11 @@ CURLcode Curl_altsvc_parse(struct Curl_easy *data,
|
|||
bool Curl_altsvc_lookup(struct altsvcinfo *asi,
|
||||
enum alpnid srcalpnid, const char *srchost,
|
||||
int srcport,
|
||||
enum alpnid *dstalpnid, const char **dsthost,
|
||||
int *dstport);
|
||||
struct altsvc **dstentry,
|
||||
const int versions); /* CURLALTSVC_H* bits */
|
||||
#else
|
||||
/* disabled */
|
||||
#define Curl_altsvc_save(a,b)
|
||||
#endif /* CURL_DISABLE_HTTP || USE_ALTSVC */
|
||||
#define Curl_altsvc_save(a,b,c)
|
||||
#define Curl_altsvc_cleanup(x)
|
||||
#endif /* !CURL_DISABLE_HTTP && !CURL_DISABLE_ALTSVC */
|
||||
#endif /* HEADER_CURL_ALTSVC_H */
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,13 +18,23 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#ifdef __AMIGA__
|
||||
# include "amigaos.h"
|
||||
# if defined(HAVE_PROTO_BSDSOCKET_H) && !defined(USE_AMISSL)
|
||||
|
||||
#include <curl/curl.h>
|
||||
|
||||
#include "hostip.h"
|
||||
#include "amigaos.h"
|
||||
|
||||
#ifdef HAVE_PROTO_BSDSOCKET_H
|
||||
# if defined(__amigaos4__)
|
||||
# include <bsdsocket/socketbasetags.h>
|
||||
# elif !defined(USE_AMISSL)
|
||||
# include <amitcp/socketbasetags.h>
|
||||
# endif
|
||||
# ifdef __libnix__
|
||||
|
@ -36,8 +46,154 @@
|
|||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
#ifdef __AMIGA__
|
||||
#if defined(HAVE_PROTO_BSDSOCKET_H) && !defined(USE_AMISSL)
|
||||
#ifdef HAVE_PROTO_BSDSOCKET_H
|
||||
|
||||
#ifdef __amigaos4__
|
||||
/*
|
||||
* AmigaOS 4.x specific code
|
||||
*/
|
||||
|
||||
/*
|
||||
* hostip4.c - Curl_ipv4_resolve_r() replacement code
|
||||
*
|
||||
* Logic that needs to be considered are the following build cases:
|
||||
* - newlib networking
|
||||
* - clib2 networking
|
||||
* - direct bsdsocket.library networking (usually AmiSSL builds)
|
||||
* Each with the threaded resolver enabled or not.
|
||||
*
|
||||
* With the threaded resolver enabled, try to use gethostbyname_r() where
|
||||
* available, otherwise (re)open bsdsocket.library and fallback to
|
||||
* gethostbyname().
|
||||
*/
|
||||
|
||||
#include <proto/bsdsocket.h>
|
||||
|
||||
static struct SocketIFace *__CurlISocket = NULL;
|
||||
static uint32 SocketFeatures = 0;
|
||||
|
||||
#define HAVE_BSDSOCKET_GETHOSTBYNAME_R 0x01
|
||||
#define HAVE_BSDSOCKET_GETADDRINFO 0x02
|
||||
|
||||
CURLcode Curl_amiga_init(void)
|
||||
{
|
||||
struct SocketIFace *ISocket;
|
||||
struct Library *base = OpenLibrary("bsdsocket.library", 4);
|
||||
|
||||
if(base) {
|
||||
ISocket = (struct SocketIFace *)GetInterface(base, "main", 1, NULL);
|
||||
if(ISocket) {
|
||||
ULONG enabled = 0;
|
||||
|
||||
SocketBaseTags(SBTM_SETVAL(SBTC_CAN_SHARE_LIBRARY_BASES), TRUE,
|
||||
SBTM_GETREF(SBTC_HAVE_GETHOSTADDR_R_API), (ULONG)&enabled,
|
||||
TAG_DONE);
|
||||
|
||||
if(enabled) {
|
||||
SocketFeatures |= HAVE_BSDSOCKET_GETHOSTBYNAME_R;
|
||||
}
|
||||
|
||||
__CurlISocket = ISocket;
|
||||
|
||||
atexit(Curl_amiga_cleanup);
|
||||
|
||||
return CURLE_OK;
|
||||
}
|
||||
CloseLibrary(base);
|
||||
}
|
||||
|
||||
return CURLE_FAILED_INIT;
|
||||
}
|
||||
|
||||
void Curl_amiga_cleanup(void)
|
||||
{
|
||||
if(__CurlISocket) {
|
||||
struct Library *base = __CurlISocket->Data.LibBase;
|
||||
DropInterface((struct Interface *)__CurlISocket);
|
||||
CloseLibrary(base);
|
||||
__CurlISocket = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef CURLRES_AMIGA
|
||||
/*
|
||||
* Because we need to handle the different cases in hostip4.c at run-time,
|
||||
* not at compile-time, based on what was detected in Curl_amiga_init(),
|
||||
* we replace it completely with our own as to not complicate the baseline
|
||||
* code. Assumes malloc/calloc/free are thread safe because Curl_he2ai()
|
||||
* allocates memory also.
|
||||
*/
|
||||
|
||||
struct Curl_addrinfo *Curl_ipv4_resolve_r(const char *hostname,
|
||||
int port)
|
||||
{
|
||||
struct Curl_addrinfo *ai = NULL;
|
||||
struct hostent *h;
|
||||
struct SocketIFace *ISocket = __CurlISocket;
|
||||
|
||||
if(SocketFeatures & HAVE_BSDSOCKET_GETHOSTBYNAME_R) {
|
||||
LONG h_errnop = 0;
|
||||
struct hostent *buf;
|
||||
|
||||
buf = calloc(1, CURL_HOSTENT_SIZE);
|
||||
if(buf) {
|
||||
h = gethostbyname_r((STRPTR)hostname, buf,
|
||||
(char *)buf + sizeof(struct hostent),
|
||||
CURL_HOSTENT_SIZE - sizeof(struct hostent),
|
||||
&h_errnop);
|
||||
if(h) {
|
||||
ai = Curl_he2ai(h, port);
|
||||
}
|
||||
free(buf);
|
||||
}
|
||||
}
|
||||
else {
|
||||
#ifdef CURLRES_THREADED
|
||||
/* gethostbyname() is not thread safe, so we need to reopen bsdsocket
|
||||
* on the thread's context
|
||||
*/
|
||||
struct Library *base = OpenLibrary("bsdsocket.library", 4);
|
||||
if(base) {
|
||||
ISocket = (struct SocketIFace *)GetInterface(base, "main", 1, NULL);
|
||||
if(ISocket) {
|
||||
h = gethostbyname((STRPTR)hostname);
|
||||
if(h) {
|
||||
ai = Curl_he2ai(h, port);
|
||||
}
|
||||
DropInterface((struct Interface *)ISocket);
|
||||
}
|
||||
CloseLibrary(base);
|
||||
}
|
||||
#else
|
||||
/* not using threaded resolver - safe to use this as-is */
|
||||
h = gethostbyname(hostname);
|
||||
if(h) {
|
||||
ai = Curl_he2ai(h, port);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
return ai;
|
||||
}
|
||||
#endif /* CURLRES_AMIGA */
|
||||
|
||||
#ifdef USE_AMISSL
|
||||
int Curl_amiga_select(int nfds, fd_set *readfds, fd_set *writefds,
|
||||
fd_set *errorfds, struct timeval *timeout)
|
||||
{
|
||||
int r = WaitSelect(nfds, readfds, writefds, errorfds, timeout, 0);
|
||||
/* Ensure Ctrl-C signal is actioned */
|
||||
if((r == -1) && (SOCKERRNO == EINTR))
|
||||
raise(SIGINT);
|
||||
return r;
|
||||
}
|
||||
#endif /* USE_AMISSL */
|
||||
|
||||
#elif !defined(USE_AMISSL) /* __amigaos4__ */
|
||||
/*
|
||||
* Amiga OS3 specific code
|
||||
*/
|
||||
|
||||
struct Library *SocketBase = NULL;
|
||||
extern int errno, h_errno;
|
||||
|
||||
|
@ -47,7 +203,7 @@ void __request(const char *msg);
|
|||
# define __request(msg) Printf(msg "\n\a")
|
||||
#endif
|
||||
|
||||
void Curl_amiga_cleanup()
|
||||
void Curl_amiga_cleanup(void)
|
||||
{
|
||||
if(SocketBase) {
|
||||
CloseLibrary(SocketBase);
|
||||
|
@ -55,41 +211,36 @@ void Curl_amiga_cleanup()
|
|||
}
|
||||
}
|
||||
|
||||
bool Curl_amiga_init()
|
||||
CURLcode Curl_amiga_init(void)
|
||||
{
|
||||
if(!SocketBase)
|
||||
SocketBase = OpenLibrary("bsdsocket.library", 4);
|
||||
|
||||
if(!SocketBase) {
|
||||
__request("No TCP/IP Stack running!");
|
||||
return FALSE;
|
||||
return CURLE_FAILED_INIT;
|
||||
}
|
||||
|
||||
if(SocketBaseTags(SBTM_SETVAL(SBTC_ERRNOPTR(sizeof(errno))), (ULONG) &errno,
|
||||
SBTM_SETVAL(SBTC_LOGTAGPTR), (ULONG) "curl",
|
||||
TAG_DONE)) {
|
||||
__request("SocketBaseTags ERROR");
|
||||
return FALSE;
|
||||
return CURLE_FAILED_INIT;
|
||||
}
|
||||
|
||||
#ifndef __libnix__
|
||||
atexit(Curl_amiga_cleanup);
|
||||
#endif
|
||||
|
||||
return TRUE;
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
#ifdef __libnix__
|
||||
ADD2EXIT(Curl_amiga_cleanup, -50);
|
||||
#endif
|
||||
|
||||
#endif /* !USE_AMISSL */
|
||||
|
||||
#endif /* HAVE_PROTO_BSDSOCKET_H */
|
||||
|
||||
#ifdef USE_AMISSL
|
||||
void Curl_amiga_X509_free(X509 *a)
|
||||
{
|
||||
X509_free(a);
|
||||
}
|
||||
#endif /* USE_AMISSL */
|
||||
#endif /* __AMIGA__ */
|
||||
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,25 +20,23 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if defined(__AMIGA__) && defined(HAVE_BSDSOCKET_H) && !defined(USE_AMISSL)
|
||||
#if defined(__AMIGA__) && defined(HAVE_PROTO_BSDSOCKET_H) && \
|
||||
(!defined(USE_AMISSL) || defined(__amigaos4__))
|
||||
|
||||
bool Curl_amiga_init();
|
||||
void Curl_amiga_cleanup();
|
||||
CURLcode Curl_amiga_init(void);
|
||||
void Curl_amiga_cleanup(void);
|
||||
|
||||
#else
|
||||
|
||||
#define Curl_amiga_init() 1
|
||||
#define Curl_amiga_init() CURLE_OK
|
||||
#define Curl_amiga_cleanup() Curl_nop_stmt
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef USE_AMISSL
|
||||
#include <openssl/x509v3.h>
|
||||
void Curl_amiga_X509_free(X509 *a);
|
||||
#endif /* USE_AMISSL */
|
||||
|
||||
#endif /* HEADER_CURL_AMIGAOS_H */
|
||||
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2018, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#ifndef CURL_DISABLE_TELNET
|
||||
/*
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -45,30 +47,21 @@
|
|||
#include <inet.h>
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_PROCESS_H
|
||||
#include <process.h>
|
||||
#endif
|
||||
|
||||
#if (defined(NETWARE) && defined(__NOVELL_LIBC__))
|
||||
#undef in_addr_t
|
||||
#define in_addr_t unsigned long
|
||||
#endif
|
||||
|
||||
#include "urldata.h"
|
||||
#include "sendf.h"
|
||||
#include "hostip.h"
|
||||
#include "hash.h"
|
||||
#include "share.h"
|
||||
#include "strerror.h"
|
||||
#include "url.h"
|
||||
#include "multiif.h"
|
||||
#include "inet_pton.h"
|
||||
#include "connect.h"
|
||||
#include "select.h"
|
||||
#include "progress.h"
|
||||
#include "timediff.h"
|
||||
|
||||
# if defined(CURL_STATICLIB) && !defined(CARES_STATICLIB) && \
|
||||
(defined(WIN32) || defined(__SYMBIAN32__))
|
||||
# if defined(CURL_STATICLIB) && !defined(CARES_STATICLIB) && \
|
||||
defined(WIN32)
|
||||
# define CARES_STATICLIB
|
||||
# endif
|
||||
# include <ares.h>
|
||||
|
@ -80,16 +73,40 @@
|
|||
#define HAVE_CARES_CALLBACK_TIMEOUTS 1
|
||||
#endif
|
||||
|
||||
#if ARES_VERSION >= 0x010601
|
||||
/* IPv6 supported since 1.6.1 */
|
||||
#define HAVE_CARES_IPV6 1
|
||||
#endif
|
||||
|
||||
#if ARES_VERSION >= 0x010704
|
||||
#define HAVE_CARES_SERVERS_CSV 1
|
||||
#define HAVE_CARES_LOCAL_DEV 1
|
||||
#define HAVE_CARES_SET_LOCAL 1
|
||||
#endif
|
||||
|
||||
#if ARES_VERSION >= 0x010b00
|
||||
#define HAVE_CARES_PORTS_CSV 1
|
||||
#endif
|
||||
|
||||
#if ARES_VERSION >= 0x011000
|
||||
/* 1.16.0 or later has ares_getaddrinfo */
|
||||
#define HAVE_CARES_GETADDRINFO 1
|
||||
#endif
|
||||
|
||||
/* The last 3 #include files should be in this order */
|
||||
#include "curl_printf.h"
|
||||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
struct ResolverResults {
|
||||
int num_pending; /* number of ares_gethostbyname() requests */
|
||||
Curl_addrinfo *temp_ai; /* intermediary result while fetching c-ares parts */
|
||||
struct thread_data {
|
||||
int num_pending; /* number of outstanding c-ares requests */
|
||||
struct Curl_addrinfo *temp_ai; /* intermediary result while fetching c-ares
|
||||
parts */
|
||||
int last_status;
|
||||
#ifndef HAVE_CARES_GETADDRINFO
|
||||
struct curltime happy_eyeballs_dns_time; /* when this timer started, or 0 */
|
||||
#endif
|
||||
char hostname[1];
|
||||
};
|
||||
|
||||
/* How long we are willing to wait for additional parallel responses after
|
||||
|
@ -132,8 +149,8 @@ void Curl_resolver_global_cleanup(void)
|
|||
}
|
||||
|
||||
|
||||
static void Curl_ares_sock_state_cb(void *data, ares_socket_t socket_fd,
|
||||
int readable, int writable)
|
||||
static void sock_state_cb(void *data, ares_socket_t socket_fd,
|
||||
int readable, int writable)
|
||||
{
|
||||
struct Curl_easy *easy = data;
|
||||
if(!readable && !writable) {
|
||||
|
@ -154,7 +171,7 @@ CURLcode Curl_resolver_init(struct Curl_easy *easy, void **resolver)
|
|||
int status;
|
||||
struct ares_options options;
|
||||
int optmask = ARES_OPT_SOCK_STATE_CB;
|
||||
options.sock_state_cb = Curl_ares_sock_state_cb;
|
||||
options.sock_state_cb = sock_state_cb;
|
||||
options.sock_state_cb_data = easy;
|
||||
status = ares_init_options((ares_channel*)resolver, &options, optmask);
|
||||
if(status != ARES_SUCCESS) {
|
||||
|
@ -203,22 +220,23 @@ static void destroy_async_data(struct Curl_async *async);
|
|||
/*
|
||||
* Cancel all possibly still on-going resolves for this connection.
|
||||
*/
|
||||
void Curl_resolver_cancel(struct connectdata *conn)
|
||||
void Curl_resolver_cancel(struct Curl_easy *data)
|
||||
{
|
||||
if(conn->data && conn->data->state.resolver)
|
||||
ares_cancel((ares_channel)conn->data->state.resolver);
|
||||
destroy_async_data(&conn->async);
|
||||
DEBUGASSERT(data);
|
||||
if(data->state.async.resolver)
|
||||
ares_cancel((ares_channel)data->state.async.resolver);
|
||||
destroy_async_data(&data->state.async);
|
||||
}
|
||||
|
||||
/*
|
||||
* We're equivalent to Curl_resolver_cancel() for the c-ares resolver. We
|
||||
* never block.
|
||||
*/
|
||||
void Curl_resolver_kill(struct connectdata *conn)
|
||||
void Curl_resolver_kill(struct Curl_easy *data)
|
||||
{
|
||||
/* We don't need to check the resolver state because we can be called safely
|
||||
at any time and we always do the same thing. */
|
||||
Curl_resolver_cancel(conn);
|
||||
Curl_resolver_cancel(data);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -226,10 +244,8 @@ void Curl_resolver_kill(struct connectdata *conn)
|
|||
*/
|
||||
static void destroy_async_data(struct Curl_async *async)
|
||||
{
|
||||
free(async->hostname);
|
||||
|
||||
if(async->os_specific) {
|
||||
struct ResolverResults *res = (struct ResolverResults *)async->os_specific;
|
||||
if(async->tdata) {
|
||||
struct thread_data *res = async->tdata;
|
||||
if(res) {
|
||||
if(res->temp_ai) {
|
||||
Curl_freeaddrinfo(res->temp_ai);
|
||||
|
@ -237,10 +253,8 @@ static void destroy_async_data(struct Curl_async *async)
|
|||
}
|
||||
free(res);
|
||||
}
|
||||
async->os_specific = NULL;
|
||||
async->tdata = NULL;
|
||||
}
|
||||
|
||||
async->hostname = NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -252,27 +266,25 @@ static void destroy_async_data(struct Curl_async *async)
|
|||
* Returns: sockets-in-use-bitmap
|
||||
*/
|
||||
|
||||
int Curl_resolver_getsock(struct connectdata *conn,
|
||||
curl_socket_t *socks,
|
||||
int numsocks)
|
||||
|
||||
int Curl_resolver_getsock(struct Curl_easy *data,
|
||||
curl_socket_t *socks)
|
||||
{
|
||||
struct timeval maxtime;
|
||||
struct timeval timebuf;
|
||||
struct timeval *timeout;
|
||||
long milli;
|
||||
int max = ares_getsock((ares_channel)conn->data->state.resolver,
|
||||
(ares_socket_t *)socks, numsocks);
|
||||
int max = ares_getsock((ares_channel)data->state.async.resolver,
|
||||
(ares_socket_t *)socks, MAX_SOCKSPEREASYHANDLE);
|
||||
|
||||
maxtime.tv_sec = CURL_TIMEOUT_RESOLVE;
|
||||
maxtime.tv_usec = 0;
|
||||
|
||||
timeout = ares_timeout((ares_channel)conn->data->state.resolver, &maxtime,
|
||||
timeout = ares_timeout((ares_channel)data->state.async.resolver, &maxtime,
|
||||
&timebuf);
|
||||
milli = (timeout->tv_sec * 1000) + (timeout->tv_usec/1000);
|
||||
milli = (long)curlx_tvtoms(timeout);
|
||||
if(milli == 0)
|
||||
milli += 10;
|
||||
Curl_expire(conn->data, milli, EXPIRE_ASYNC_NAME);
|
||||
Curl_expire(data, milli, EXPIRE_ASYNC_NAME);
|
||||
|
||||
return max;
|
||||
}
|
||||
|
@ -284,12 +296,11 @@ int Curl_resolver_getsock(struct connectdata *conn,
|
|||
* 2) wait for the timeout period to check for action on ares' sockets.
|
||||
* 3) tell ares to act on all the sockets marked as "with action"
|
||||
*
|
||||
* return number of sockets it worked on
|
||||
* return number of sockets it worked on, or -1 on error
|
||||
*/
|
||||
|
||||
static int waitperform(struct connectdata *conn, int timeout_ms)
|
||||
static int waitperform(struct Curl_easy *data, timediff_t timeout_ms)
|
||||
{
|
||||
struct Curl_easy *data = conn->data;
|
||||
int nfds;
|
||||
int bitmask;
|
||||
ares_socket_t socks[ARES_GETSOCK_MAXNUM];
|
||||
|
@ -297,7 +308,7 @@ static int waitperform(struct connectdata *conn, int timeout_ms)
|
|||
int i;
|
||||
int num = 0;
|
||||
|
||||
bitmask = ares_getsock((ares_channel)data->state.resolver, socks,
|
||||
bitmask = ares_getsock((ares_channel)data->state.async.resolver, socks,
|
||||
ARES_GETSOCK_MAXNUM);
|
||||
|
||||
for(i = 0; i < ARES_GETSOCK_MAXNUM; i++) {
|
||||
|
@ -311,26 +322,29 @@ static int waitperform(struct connectdata *conn, int timeout_ms)
|
|||
pfd[i].fd = socks[i];
|
||||
pfd[i].events |= POLLWRNORM|POLLOUT;
|
||||
}
|
||||
if(pfd[i].events != 0)
|
||||
if(pfd[i].events)
|
||||
num++;
|
||||
else
|
||||
break;
|
||||
}
|
||||
|
||||
if(num)
|
||||
if(num) {
|
||||
nfds = Curl_poll(pfd, num, timeout_ms);
|
||||
if(nfds < 0)
|
||||
return -1;
|
||||
}
|
||||
else
|
||||
nfds = 0;
|
||||
|
||||
if(!nfds)
|
||||
/* Call ares_process() unconditonally here, even if we simply timed out
|
||||
/* Call ares_process() unconditionally here, even if we simply timed out
|
||||
above, as otherwise the ares name resolve won't timeout! */
|
||||
ares_process_fd((ares_channel)data->state.resolver, ARES_SOCKET_BAD,
|
||||
ares_process_fd((ares_channel)data->state.async.resolver, ARES_SOCKET_BAD,
|
||||
ARES_SOCKET_BAD);
|
||||
else {
|
||||
/* move through the descriptors and ask for processing on them */
|
||||
for(i = 0; i < num; i++)
|
||||
ares_process_fd((ares_channel)data->state.resolver,
|
||||
ares_process_fd((ares_channel)data->state.async.resolver,
|
||||
(pfd[i].revents & (POLLRDNORM|POLLIN))?
|
||||
pfd[i].fd:ARES_SOCKET_BAD,
|
||||
(pfd[i].revents & (POLLWRNORM|POLLOUT))?
|
||||
|
@ -346,19 +360,19 @@ static int waitperform(struct connectdata *conn, int timeout_ms)
|
|||
*
|
||||
* Returns normal CURLcode errors.
|
||||
*/
|
||||
CURLcode Curl_resolver_is_resolved(struct connectdata *conn,
|
||||
CURLcode Curl_resolver_is_resolved(struct Curl_easy *data,
|
||||
struct Curl_dns_entry **dns)
|
||||
{
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct ResolverResults *res = (struct ResolverResults *)
|
||||
conn->async.os_specific;
|
||||
struct thread_data *res = data->state.async.tdata;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
if(dns)
|
||||
*dns = NULL;
|
||||
DEBUGASSERT(dns);
|
||||
*dns = NULL;
|
||||
|
||||
waitperform(conn, 0);
|
||||
if(waitperform(data, 0) < 0)
|
||||
return CURLE_UNRECOVERABLE_POLL;
|
||||
|
||||
#ifndef HAVE_CARES_GETADDRINFO
|
||||
/* Now that we've checked for any last minute results above, see if there are
|
||||
any responses still pending when the EXPIRE_HAPPY_EYEBALLS_DNS timer
|
||||
expires. */
|
||||
|
@ -378,27 +392,23 @@ CURLcode Curl_resolver_is_resolved(struct connectdata *conn,
|
|||
ARES_ECANCELLED synchronously for all pending responses. This will
|
||||
leave us with res->num_pending == 0, which is perfect for the next
|
||||
block. */
|
||||
ares_cancel((ares_channel)data->state.resolver);
|
||||
ares_cancel((ares_channel)data->state.async.resolver);
|
||||
DEBUGASSERT(res->num_pending == 0);
|
||||
}
|
||||
#endif
|
||||
|
||||
if(res && !res->num_pending) {
|
||||
if(dns) {
|
||||
(void)Curl_addrinfo_callback(conn, res->last_status, res->temp_ai);
|
||||
/* temp_ai ownership is moved to the connection, so we need not free-up
|
||||
them */
|
||||
res->temp_ai = NULL;
|
||||
}
|
||||
if(!conn->async.dns) {
|
||||
failf(data, "Could not resolve: %s (%s)",
|
||||
conn->async.hostname, ares_strerror(conn->async.status));
|
||||
result = conn->bits.proxy?CURLE_COULDNT_RESOLVE_PROXY:
|
||||
CURLE_COULDNT_RESOLVE_HOST;
|
||||
}
|
||||
else if(dns)
|
||||
*dns = conn->async.dns;
|
||||
(void)Curl_addrinfo_callback(data, res->last_status, res->temp_ai);
|
||||
/* temp_ai ownership is moved to the connection, so we need not free-up
|
||||
them */
|
||||
res->temp_ai = NULL;
|
||||
|
||||
destroy_async_data(&conn->async);
|
||||
if(!data->state.async.dns)
|
||||
result = Curl_resolver_error(data);
|
||||
else
|
||||
*dns = data->state.async.dns;
|
||||
|
||||
destroy_async_data(&data->state.async);
|
||||
}
|
||||
|
||||
return result;
|
||||
|
@ -410,27 +420,25 @@ CURLcode Curl_resolver_is_resolved(struct connectdata *conn,
|
|||
* Waits for a resolve to finish. This function should be avoided since using
|
||||
* this risk getting the multi interface to "hang".
|
||||
*
|
||||
* If 'entry' is non-NULL, make it point to the resolved dns entry
|
||||
* 'entry' MUST be non-NULL.
|
||||
*
|
||||
* Returns CURLE_COULDNT_RESOLVE_HOST if the host was not resolved,
|
||||
* CURLE_OPERATION_TIMEDOUT if a time-out occurred, or other errors.
|
||||
*/
|
||||
CURLcode Curl_resolver_wait_resolv(struct connectdata *conn,
|
||||
CURLcode Curl_resolver_wait_resolv(struct Curl_easy *data,
|
||||
struct Curl_dns_entry **entry)
|
||||
{
|
||||
CURLcode result = CURLE_OK;
|
||||
struct Curl_easy *data = conn->data;
|
||||
timediff_t timeout;
|
||||
struct curltime now = Curl_now();
|
||||
struct Curl_dns_entry *temp_entry;
|
||||
|
||||
if(entry)
|
||||
*entry = NULL; /* clear on entry */
|
||||
DEBUGASSERT(entry);
|
||||
*entry = NULL; /* clear on entry */
|
||||
|
||||
timeout = Curl_timeleft(data, &now, TRUE);
|
||||
if(timeout < 0) {
|
||||
/* already expired! */
|
||||
connclose(conn, "Timed out before name resolve started");
|
||||
connclose(data->conn, "Timed out before name resolve started");
|
||||
return CURLE_OPERATION_TIMEDOUT;
|
||||
}
|
||||
if(!timeout)
|
||||
|
@ -440,30 +448,35 @@ CURLcode Curl_resolver_wait_resolv(struct connectdata *conn,
|
|||
while(!result) {
|
||||
struct timeval *tvp, tv, store;
|
||||
int itimeout;
|
||||
int timeout_ms;
|
||||
timediff_t timeout_ms;
|
||||
|
||||
itimeout = (timeout > (long)INT_MAX) ? INT_MAX : (int)timeout;
|
||||
#if TIMEDIFF_T_MAX > INT_MAX
|
||||
itimeout = (timeout > INT_MAX) ? INT_MAX : (int)timeout;
|
||||
#else
|
||||
itimeout = (int)timeout;
|
||||
#endif
|
||||
|
||||
store.tv_sec = itimeout/1000;
|
||||
store.tv_usec = (itimeout%1000)*1000;
|
||||
|
||||
tvp = ares_timeout((ares_channel)data->state.resolver, &store, &tv);
|
||||
tvp = ares_timeout((ares_channel)data->state.async.resolver, &store, &tv);
|
||||
|
||||
/* use the timeout period ares returned to us above if less than one
|
||||
second is left, otherwise just use 1000ms to make sure the progress
|
||||
callback gets called frequent enough */
|
||||
if(!tvp->tv_sec)
|
||||
timeout_ms = (int)(tvp->tv_usec/1000);
|
||||
timeout_ms = (timediff_t)(tvp->tv_usec/1000);
|
||||
else
|
||||
timeout_ms = 1000;
|
||||
|
||||
waitperform(conn, timeout_ms);
|
||||
result = Curl_resolver_is_resolved(conn, entry?&temp_entry:NULL);
|
||||
if(waitperform(data, timeout_ms) < 0)
|
||||
return CURLE_UNRECOVERABLE_POLL;
|
||||
result = Curl_resolver_is_resolved(data, entry);
|
||||
|
||||
if(result || conn->async.done)
|
||||
if(result || data->state.async.done)
|
||||
break;
|
||||
|
||||
if(Curl_pgrsUpdate(conn))
|
||||
if(Curl_pgrsUpdate(data))
|
||||
result = CURLE_ABORTED_BY_CALLBACK;
|
||||
else {
|
||||
struct curltime now2 = Curl_now();
|
||||
|
@ -473,7 +486,7 @@ CURLcode Curl_resolver_wait_resolv(struct connectdata *conn,
|
|||
else if(timediff > timeout)
|
||||
timeout = -1;
|
||||
else
|
||||
timeout -= (long)timediff;
|
||||
timeout -= timediff;
|
||||
now = now2; /* for next loop */
|
||||
}
|
||||
if(timeout < 0)
|
||||
|
@ -481,36 +494,52 @@ CURLcode Curl_resolver_wait_resolv(struct connectdata *conn,
|
|||
}
|
||||
if(result)
|
||||
/* failure, so we cancel the ares operation */
|
||||
ares_cancel((ares_channel)data->state.resolver);
|
||||
ares_cancel((ares_channel)data->state.async.resolver);
|
||||
|
||||
/* Operation complete, if the lookup was successful we now have the entry
|
||||
in the cache. */
|
||||
if(entry)
|
||||
*entry = conn->async.dns;
|
||||
*entry = data->state.async.dns;
|
||||
|
||||
if(result)
|
||||
/* close the connection, since we can't return failure here without
|
||||
cleaning up this connection properly. */
|
||||
connclose(conn, "c-ares resolve failed");
|
||||
connclose(data->conn, "c-ares resolve failed");
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
#ifndef HAVE_CARES_GETADDRINFO
|
||||
|
||||
/* Connects results to the list */
|
||||
static void compound_results(struct ResolverResults *res,
|
||||
Curl_addrinfo *ai)
|
||||
static void compound_results(struct thread_data *res,
|
||||
struct Curl_addrinfo *ai)
|
||||
{
|
||||
Curl_addrinfo *ai_tail;
|
||||
if(!ai)
|
||||
return;
|
||||
ai_tail = ai;
|
||||
|
||||
while(ai_tail->ai_next)
|
||||
ai_tail = ai_tail->ai_next;
|
||||
#ifdef ENABLE_IPV6 /* CURLRES_IPV6 */
|
||||
if(res->temp_ai && res->temp_ai->ai_family == PF_INET6) {
|
||||
/* We have results already, put the new IPv6 entries at the head of the
|
||||
list. */
|
||||
struct Curl_addrinfo *temp_ai_tail = res->temp_ai;
|
||||
|
||||
/* Add the new results to the list of old results. */
|
||||
ai_tail->ai_next = res->temp_ai;
|
||||
res->temp_ai = ai;
|
||||
while(temp_ai_tail->ai_next)
|
||||
temp_ai_tail = temp_ai_tail->ai_next;
|
||||
|
||||
temp_ai_tail->ai_next = ai;
|
||||
}
|
||||
else
|
||||
#endif /* CURLRES_IPV6 */
|
||||
{
|
||||
/* Add the new results to the list of old results. */
|
||||
struct Curl_addrinfo *ai_tail = ai;
|
||||
while(ai_tail->ai_next)
|
||||
ai_tail = ai_tail->ai_next;
|
||||
|
||||
ai_tail->ai_next = res->temp_ai;
|
||||
res->temp_ai = ai;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -525,8 +554,8 @@ static void query_completed_cb(void *arg, /* (struct connectdata *) */
|
|||
#endif
|
||||
struct hostent *hostent)
|
||||
{
|
||||
struct connectdata *conn = (struct connectdata *)arg;
|
||||
struct ResolverResults *res;
|
||||
struct Curl_easy *data = (struct Curl_easy *)arg;
|
||||
struct thread_data *res;
|
||||
|
||||
#ifdef HAVE_CARES_CALLBACK_TIMEOUTS
|
||||
(void)timeouts; /* ignored */
|
||||
|
@ -537,12 +566,12 @@ static void query_completed_cb(void *arg, /* (struct connectdata *) */
|
|||
be valid so only defer it when we know the 'status' says its fine! */
|
||||
return;
|
||||
|
||||
res = (struct ResolverResults *)conn->async.os_specific;
|
||||
res = data->state.async.tdata;
|
||||
if(res) {
|
||||
res->num_pending--;
|
||||
|
||||
if(CURL_ASYNC_SUCCESS == status) {
|
||||
Curl_addrinfo *ai = Curl_he2ai(hostent, conn->async.port);
|
||||
struct Curl_addrinfo *ai = Curl_he2ai(hostent, data->state.async.port);
|
||||
if(ai) {
|
||||
compound_results(res, ai);
|
||||
}
|
||||
|
@ -607,112 +636,180 @@ static void query_completed_cb(void *arg, /* (struct connectdata *) */
|
|||
c-ares retry cycle each request is.
|
||||
*/
|
||||
res->happy_eyeballs_dns_time = Curl_now();
|
||||
Curl_expire(
|
||||
conn->data, HAPPY_EYEBALLS_DNS_TIMEOUT, EXPIRE_HAPPY_EYEBALLS_DNS);
|
||||
Curl_expire(data, HAPPY_EYEBALLS_DNS_TIMEOUT,
|
||||
EXPIRE_HAPPY_EYEBALLS_DNS);
|
||||
}
|
||||
}
|
||||
}
|
||||
#else
|
||||
/* c-ares 1.16.0 or later */
|
||||
|
||||
/*
|
||||
* ares2addr() converts an address list provided by c-ares to an internal
|
||||
* libcurl compatible list
|
||||
*/
|
||||
static struct Curl_addrinfo *ares2addr(struct ares_addrinfo_node *node)
|
||||
{
|
||||
/* traverse the ares_addrinfo_node list */
|
||||
struct ares_addrinfo_node *ai;
|
||||
struct Curl_addrinfo *cafirst = NULL;
|
||||
struct Curl_addrinfo *calast = NULL;
|
||||
int error = 0;
|
||||
|
||||
for(ai = node; ai != NULL; ai = ai->ai_next) {
|
||||
size_t ss_size;
|
||||
struct Curl_addrinfo *ca;
|
||||
/* ignore elements with unsupported address family, */
|
||||
/* settle family-specific sockaddr structure size. */
|
||||
if(ai->ai_family == AF_INET)
|
||||
ss_size = sizeof(struct sockaddr_in);
|
||||
#ifdef ENABLE_IPV6
|
||||
else if(ai->ai_family == AF_INET6)
|
||||
ss_size = sizeof(struct sockaddr_in6);
|
||||
#endif
|
||||
else
|
||||
continue;
|
||||
|
||||
/* ignore elements without required address info */
|
||||
if(!ai->ai_addr || !(ai->ai_addrlen > 0))
|
||||
continue;
|
||||
|
||||
/* ignore elements with bogus address size */
|
||||
if((size_t)ai->ai_addrlen < ss_size)
|
||||
continue;
|
||||
|
||||
ca = malloc(sizeof(struct Curl_addrinfo) + ss_size);
|
||||
if(!ca) {
|
||||
error = EAI_MEMORY;
|
||||
break;
|
||||
}
|
||||
|
||||
/* copy each structure member individually, member ordering, */
|
||||
/* size, or padding might be different for each platform. */
|
||||
|
||||
ca->ai_flags = ai->ai_flags;
|
||||
ca->ai_family = ai->ai_family;
|
||||
ca->ai_socktype = ai->ai_socktype;
|
||||
ca->ai_protocol = ai->ai_protocol;
|
||||
ca->ai_addrlen = (curl_socklen_t)ss_size;
|
||||
ca->ai_addr = NULL;
|
||||
ca->ai_canonname = NULL;
|
||||
ca->ai_next = NULL;
|
||||
|
||||
ca->ai_addr = (void *)((char *)ca + sizeof(struct Curl_addrinfo));
|
||||
memcpy(ca->ai_addr, ai->ai_addr, ss_size);
|
||||
|
||||
/* if the return list is empty, this becomes the first element */
|
||||
if(!cafirst)
|
||||
cafirst = ca;
|
||||
|
||||
/* add this element last in the return list */
|
||||
if(calast)
|
||||
calast->ai_next = ca;
|
||||
calast = ca;
|
||||
}
|
||||
|
||||
/* if we failed, destroy the Curl_addrinfo list */
|
||||
if(error) {
|
||||
Curl_freeaddrinfo(cafirst);
|
||||
cafirst = NULL;
|
||||
}
|
||||
|
||||
return cafirst;
|
||||
}
|
||||
|
||||
static void addrinfo_cb(void *arg, int status, int timeouts,
|
||||
struct ares_addrinfo *result)
|
||||
{
|
||||
struct Curl_easy *data = (struct Curl_easy *)arg;
|
||||
struct thread_data *res = data->state.async.tdata;
|
||||
(void)timeouts;
|
||||
if(ARES_SUCCESS == status) {
|
||||
res->temp_ai = ares2addr(result->nodes);
|
||||
res->last_status = CURL_ASYNC_SUCCESS;
|
||||
ares_freeaddrinfo(result);
|
||||
}
|
||||
res->num_pending--;
|
||||
}
|
||||
|
||||
#endif
|
||||
/*
|
||||
* Curl_resolver_getaddrinfo() - when using ares
|
||||
*
|
||||
* Returns name information about the given hostname and port number. If
|
||||
* successful, the 'hostent' is returned and the forth argument will point to
|
||||
* successful, the 'hostent' is returned and the fourth argument will point to
|
||||
* memory we need to free after use. That memory *MUST* be freed with
|
||||
* Curl_freeaddrinfo(), nothing else.
|
||||
*/
|
||||
Curl_addrinfo *Curl_resolver_getaddrinfo(struct connectdata *conn,
|
||||
const char *hostname,
|
||||
int port,
|
||||
int *waitp)
|
||||
struct Curl_addrinfo *Curl_resolver_getaddrinfo(struct Curl_easy *data,
|
||||
const char *hostname,
|
||||
int port,
|
||||
int *waitp)
|
||||
{
|
||||
char *bufp;
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct in_addr in;
|
||||
int family = PF_INET;
|
||||
#ifdef ENABLE_IPV6 /* CURLRES_IPV6 */
|
||||
struct in6_addr in6;
|
||||
#endif /* CURLRES_IPV6 */
|
||||
|
||||
struct thread_data *res = NULL;
|
||||
size_t namelen = strlen(hostname);
|
||||
*waitp = 0; /* default to synchronous response */
|
||||
|
||||
/* First check if this is an IPv4 address string */
|
||||
if(Curl_inet_pton(AF_INET, hostname, &in) > 0) {
|
||||
/* This is a dotted IP address 123.123.123.123-style */
|
||||
return Curl_ip2addr(AF_INET, &in, hostname, port);
|
||||
}
|
||||
|
||||
#ifdef ENABLE_IPV6 /* CURLRES_IPV6 */
|
||||
/* Otherwise, check if this is an IPv6 address string */
|
||||
if(Curl_inet_pton (AF_INET6, hostname, &in6) > 0)
|
||||
/* This must be an IPv6 address literal. */
|
||||
return Curl_ip2addr(AF_INET6, &in6, hostname, port);
|
||||
|
||||
switch(conn->ip_version) {
|
||||
default:
|
||||
#if ARES_VERSION >= 0x010601
|
||||
family = PF_UNSPEC; /* supported by c-ares since 1.6.1, so for older
|
||||
c-ares versions this just falls through and defaults
|
||||
to PF_INET */
|
||||
break;
|
||||
#endif
|
||||
case CURL_IPRESOLVE_V4:
|
||||
family = PF_INET;
|
||||
break;
|
||||
case CURL_IPRESOLVE_V6:
|
||||
family = PF_INET6;
|
||||
break;
|
||||
}
|
||||
#endif /* CURLRES_IPV6 */
|
||||
|
||||
bufp = strdup(hostname);
|
||||
if(bufp) {
|
||||
struct ResolverResults *res = NULL;
|
||||
free(conn->async.hostname);
|
||||
conn->async.hostname = bufp;
|
||||
conn->async.port = port;
|
||||
conn->async.done = FALSE; /* not done */
|
||||
conn->async.status = 0; /* clear */
|
||||
conn->async.dns = NULL; /* clear */
|
||||
res = calloc(sizeof(struct ResolverResults), 1);
|
||||
if(!res) {
|
||||
free(conn->async.hostname);
|
||||
conn->async.hostname = NULL;
|
||||
return NULL;
|
||||
}
|
||||
conn->async.os_specific = res;
|
||||
res = calloc(sizeof(struct thread_data) + namelen, 1);
|
||||
if(res) {
|
||||
strcpy(res->hostname, hostname);
|
||||
data->state.async.hostname = res->hostname;
|
||||
data->state.async.port = port;
|
||||
data->state.async.done = FALSE; /* not done */
|
||||
data->state.async.status = 0; /* clear */
|
||||
data->state.async.dns = NULL; /* clear */
|
||||
data->state.async.tdata = res;
|
||||
|
||||
/* initial status - failed */
|
||||
res->last_status = ARES_ENOTFOUND;
|
||||
#ifdef ENABLE_IPV6 /* CURLRES_IPV6 */
|
||||
if(family == PF_UNSPEC) {
|
||||
if(Curl_ipv6works()) {
|
||||
res->num_pending = 2;
|
||||
|
||||
/* areschannel is already setup in the Curl_open() function */
|
||||
ares_gethostbyname((ares_channel)data->state.resolver, hostname,
|
||||
PF_INET, query_completed_cb, conn);
|
||||
ares_gethostbyname((ares_channel)data->state.resolver, hostname,
|
||||
PF_INET6, query_completed_cb, conn);
|
||||
}
|
||||
else {
|
||||
res->num_pending = 1;
|
||||
#ifdef HAVE_CARES_GETADDRINFO
|
||||
{
|
||||
struct ares_addrinfo_hints hints;
|
||||
char service[12];
|
||||
int pf = PF_INET;
|
||||
memset(&hints, 0, sizeof(hints));
|
||||
#ifdef CURLRES_IPV6
|
||||
if((data->conn->ip_version != CURL_IPRESOLVE_V4) && Curl_ipv6works(data))
|
||||
/* The stack seems to be IPv6-enabled */
|
||||
pf = PF_UNSPEC;
|
||||
#endif /* CURLRES_IPV6 */
|
||||
hints.ai_family = pf;
|
||||
hints.ai_socktype = (data->conn->transport == TRNSPRT_TCP)?
|
||||
SOCK_STREAM : SOCK_DGRAM;
|
||||
/* Since the service is a numerical one, set the hint flags
|
||||
* accordingly to save a call to getservbyname in inside C-Ares
|
||||
*/
|
||||
hints.ai_flags = ARES_AI_NUMERICSERV;
|
||||
msnprintf(service, sizeof(service), "%d", port);
|
||||
res->num_pending = 1;
|
||||
ares_getaddrinfo((ares_channel)data->state.async.resolver, hostname,
|
||||
service, &hints, addrinfo_cb, data);
|
||||
}
|
||||
#else
|
||||
|
||||
/* areschannel is already setup in the Curl_open() function */
|
||||
ares_gethostbyname((ares_channel)data->state.resolver, hostname,
|
||||
PF_INET, query_completed_cb, conn);
|
||||
}
|
||||
#ifdef HAVE_CARES_IPV6
|
||||
if((data->conn->ip_version != CURL_IPRESOLVE_V4) && Curl_ipv6works(data)) {
|
||||
/* The stack seems to be IPv6-enabled */
|
||||
res->num_pending = 2;
|
||||
|
||||
/* areschannel is already setup in the Curl_open() function */
|
||||
ares_gethostbyname((ares_channel)data->state.async.resolver, hostname,
|
||||
PF_INET, query_completed_cb, data);
|
||||
ares_gethostbyname((ares_channel)data->state.async.resolver, hostname,
|
||||
PF_INET6, query_completed_cb, data);
|
||||
}
|
||||
else
|
||||
#endif /* CURLRES_IPV6 */
|
||||
#endif
|
||||
{
|
||||
res->num_pending = 1;
|
||||
|
||||
/* areschannel is already setup in the Curl_open() function */
|
||||
ares_gethostbyname((ares_channel)data->state.resolver, hostname, family,
|
||||
query_completed_cb, conn);
|
||||
ares_gethostbyname((ares_channel)data->state.async.resolver,
|
||||
hostname, PF_INET,
|
||||
query_completed_cb, data);
|
||||
}
|
||||
|
||||
#endif
|
||||
*waitp = 1; /* expect asynchronous response */
|
||||
}
|
||||
return NULL; /* no struct yet */
|
||||
|
@ -733,8 +830,13 @@ CURLcode Curl_set_dns_servers(struct Curl_easy *data,
|
|||
if(!(servers && servers[0]))
|
||||
return CURLE_OK;
|
||||
|
||||
#if (ARES_VERSION >= 0x010704)
|
||||
ares_result = ares_set_servers_csv(data->state.resolver, servers);
|
||||
#ifdef HAVE_CARES_SERVERS_CSV
|
||||
#ifdef HAVE_CARES_PORTS_CSV
|
||||
ares_result = ares_set_servers_ports_csv(data->state.async.resolver,
|
||||
servers);
|
||||
#else
|
||||
ares_result = ares_set_servers_csv(data->state.async.resolver, servers);
|
||||
#endif
|
||||
switch(ares_result) {
|
||||
case ARES_SUCCESS:
|
||||
result = CURLE_OK;
|
||||
|
@ -759,11 +861,11 @@ CURLcode Curl_set_dns_servers(struct Curl_easy *data,
|
|||
CURLcode Curl_set_dns_interface(struct Curl_easy *data,
|
||||
const char *interf)
|
||||
{
|
||||
#if (ARES_VERSION >= 0x010704)
|
||||
#ifdef HAVE_CARES_LOCAL_DEV
|
||||
if(!interf)
|
||||
interf = "";
|
||||
|
||||
ares_set_local_dev((ares_channel)data->state.resolver, interf);
|
||||
ares_set_local_dev((ares_channel)data->state.async.resolver, interf);
|
||||
|
||||
return CURLE_OK;
|
||||
#else /* c-ares version too old! */
|
||||
|
@ -776,7 +878,7 @@ CURLcode Curl_set_dns_interface(struct Curl_easy *data,
|
|||
CURLcode Curl_set_dns_local_ip4(struct Curl_easy *data,
|
||||
const char *local_ip4)
|
||||
{
|
||||
#if (ARES_VERSION >= 0x010704)
|
||||
#ifdef HAVE_CARES_SET_LOCAL
|
||||
struct in_addr a4;
|
||||
|
||||
if((!local_ip4) || (local_ip4[0] == 0)) {
|
||||
|
@ -788,7 +890,8 @@ CURLcode Curl_set_dns_local_ip4(struct Curl_easy *data,
|
|||
}
|
||||
}
|
||||
|
||||
ares_set_local_ip4((ares_channel)data->state.resolver, ntohl(a4.s_addr));
|
||||
ares_set_local_ip4((ares_channel)data->state.async.resolver,
|
||||
ntohl(a4.s_addr));
|
||||
|
||||
return CURLE_OK;
|
||||
#else /* c-ares version too old! */
|
||||
|
@ -801,7 +904,7 @@ CURLcode Curl_set_dns_local_ip4(struct Curl_easy *data,
|
|||
CURLcode Curl_set_dns_local_ip6(struct Curl_easy *data,
|
||||
const char *local_ip6)
|
||||
{
|
||||
#if (ARES_VERSION >= 0x010704) && defined(ENABLE_IPV6)
|
||||
#if defined(HAVE_CARES_SET_LOCAL) && defined(ENABLE_IPV6)
|
||||
unsigned char a6[INET6_ADDRSTRLEN];
|
||||
|
||||
if((!local_ip6) || (local_ip6[0] == 0)) {
|
||||
|
@ -814,7 +917,7 @@ CURLcode Curl_set_dns_local_ip6(struct Curl_easy *data,
|
|||
}
|
||||
}
|
||||
|
||||
ares_set_local_ip6((ares_channel)data->state.resolver, a6);
|
||||
ares_set_local_ip6((ares_channel)data->state.async.resolver, a6);
|
||||
|
||||
return CURLE_OK;
|
||||
#else /* c-ares version too old! */
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,9 +18,12 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
#include "socketpair.h"
|
||||
|
||||
/***********************************************************************
|
||||
* Only for threaded name resolves builds
|
||||
|
@ -41,19 +44,8 @@
|
|||
#include <inet.h>
|
||||
#endif
|
||||
|
||||
#if defined(USE_THREADS_POSIX)
|
||||
# ifdef HAVE_PTHREAD_H
|
||||
# include <pthread.h>
|
||||
# endif
|
||||
#elif defined(USE_THREADS_WIN32)
|
||||
# ifdef HAVE_PROCESS_H
|
||||
# include <process.h>
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#if (defined(NETWARE) && defined(__NOVELL_LIBC__))
|
||||
#undef in_addr_t
|
||||
#define in_addr_t unsigned long
|
||||
#if defined(USE_THREADS_POSIX) && defined(HAVE_PTHREAD_H)
|
||||
# include <pthread.h>
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_GETADDRINFO
|
||||
|
@ -67,10 +59,8 @@
|
|||
#include "hostip.h"
|
||||
#include "hash.h"
|
||||
#include "share.h"
|
||||
#include "strerror.h"
|
||||
#include "url.h"
|
||||
#include "multiif.h"
|
||||
#include "inet_pton.h"
|
||||
#include "inet_ntop.h"
|
||||
#include "curl_threads.h"
|
||||
#include "connect.h"
|
||||
|
@ -144,27 +134,30 @@ static void destroy_async_data(struct Curl_async *);
|
|||
/*
|
||||
* Cancel all possibly still on-going resolves for this connection.
|
||||
*/
|
||||
void Curl_resolver_cancel(struct connectdata *conn)
|
||||
void Curl_resolver_cancel(struct Curl_easy *data)
|
||||
{
|
||||
destroy_async_data(&conn->async);
|
||||
destroy_async_data(&data->state.async);
|
||||
}
|
||||
|
||||
/* This function is used to init a threaded resolve */
|
||||
static bool init_resolve_thread(struct connectdata *conn,
|
||||
static bool init_resolve_thread(struct Curl_easy *data,
|
||||
const char *hostname, int port,
|
||||
const struct addrinfo *hints);
|
||||
|
||||
|
||||
/* Data for synchronization between resolver thread and its parent */
|
||||
struct thread_sync_data {
|
||||
curl_mutex_t * mtx;
|
||||
curl_mutex_t *mtx;
|
||||
int done;
|
||||
|
||||
int port;
|
||||
char *hostname; /* hostname to resolve, Curl_async.hostname
|
||||
duplicate */
|
||||
int port;
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
struct Curl_easy *data;
|
||||
curl_socket_t sock_pair[2]; /* socket pair */
|
||||
#endif
|
||||
int sock_error;
|
||||
Curl_addrinfo *res;
|
||||
struct Curl_addrinfo *res;
|
||||
#ifdef HAVE_GETADDRINFO
|
||||
struct addrinfo hints;
|
||||
#endif
|
||||
|
@ -174,18 +167,18 @@ struct thread_sync_data {
|
|||
struct thread_data {
|
||||
curl_thread_t thread_hnd;
|
||||
unsigned int poll_interval;
|
||||
time_t interval_end;
|
||||
timediff_t interval_end;
|
||||
struct thread_sync_data tsd;
|
||||
};
|
||||
|
||||
static struct thread_sync_data *conn_thread_sync_data(struct connectdata *conn)
|
||||
static struct thread_sync_data *conn_thread_sync_data(struct Curl_easy *data)
|
||||
{
|
||||
return &(((struct thread_data *)conn->async.os_specific)->tsd);
|
||||
return &(data->state.async.tdata->tsd);
|
||||
}
|
||||
|
||||
/* Destroy resolver thread synchronization data */
|
||||
static
|
||||
void destroy_thread_sync_data(struct thread_sync_data * tsd)
|
||||
void destroy_thread_sync_data(struct thread_sync_data *tsd)
|
||||
{
|
||||
if(tsd->mtx) {
|
||||
Curl_mutex_destroy(tsd->mtx);
|
||||
|
@ -197,12 +190,21 @@ void destroy_thread_sync_data(struct thread_sync_data * tsd)
|
|||
if(tsd->res)
|
||||
Curl_freeaddrinfo(tsd->res);
|
||||
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
/*
|
||||
* close one end of the socket pair (may be done in resolver thread);
|
||||
* the other end (for reading) is always closed in the parent thread.
|
||||
*/
|
||||
if(tsd->sock_pair[1] != CURL_SOCKET_BAD) {
|
||||
sclose(tsd->sock_pair[1]);
|
||||
}
|
||||
#endif
|
||||
memset(tsd, 0, sizeof(*tsd));
|
||||
}
|
||||
|
||||
/* Initialize resolver thread synchronization data */
|
||||
static
|
||||
int init_thread_sync_data(struct thread_data * td,
|
||||
int init_thread_sync_data(struct thread_data *td,
|
||||
const char *hostname,
|
||||
int port,
|
||||
const struct addrinfo *hints)
|
||||
|
@ -225,11 +227,19 @@ int init_thread_sync_data(struct thread_data * td,
|
|||
#endif
|
||||
|
||||
tsd->mtx = malloc(sizeof(curl_mutex_t));
|
||||
if(tsd->mtx == NULL)
|
||||
if(!tsd->mtx)
|
||||
goto err_exit;
|
||||
|
||||
Curl_mutex_init(tsd->mtx);
|
||||
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
/* create socket pair, avoid AF_LOCAL since it doesn't build on Solaris */
|
||||
if(Curl_socketpair(AF_UNIX, SOCK_STREAM, 0, &tsd->sock_pair[0]) < 0) {
|
||||
tsd->sock_pair[0] = CURL_SOCKET_BAD;
|
||||
tsd->sock_pair[1] = CURL_SOCKET_BAD;
|
||||
goto err_exit;
|
||||
}
|
||||
#endif
|
||||
tsd->sock_error = CURL_ASYNC_SUCCESS;
|
||||
|
||||
/* Copying hostname string because original can be destroyed by parent
|
||||
|
@ -242,23 +252,28 @@ int init_thread_sync_data(struct thread_data * td,
|
|||
return 1;
|
||||
|
||||
err_exit:
|
||||
/* Memory allocation failed */
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
if(tsd->sock_pair[0] != CURL_SOCKET_BAD) {
|
||||
sclose(tsd->sock_pair[0]);
|
||||
tsd->sock_pair[0] = CURL_SOCKET_BAD;
|
||||
}
|
||||
#endif
|
||||
destroy_thread_sync_data(tsd);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int getaddrinfo_complete(struct connectdata *conn)
|
||||
static CURLcode getaddrinfo_complete(struct Curl_easy *data)
|
||||
{
|
||||
struct thread_sync_data *tsd = conn_thread_sync_data(conn);
|
||||
int rc;
|
||||
struct thread_sync_data *tsd = conn_thread_sync_data(data);
|
||||
CURLcode result;
|
||||
|
||||
rc = Curl_addrinfo_callback(conn, tsd->sock_error, tsd->res);
|
||||
result = Curl_addrinfo_callback(data, tsd->sock_error, tsd->res);
|
||||
/* The tsd->res structure has been copied to async.dns and perhaps the DNS
|
||||
cache. Set our copy to NULL so destroy_thread_sync_data doesn't free it.
|
||||
*/
|
||||
tsd->res = NULL;
|
||||
|
||||
return rc;
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
|
@ -272,16 +287,19 @@ static int getaddrinfo_complete(struct connectdata *conn)
|
|||
*/
|
||||
static unsigned int CURL_STDCALL getaddrinfo_thread(void *arg)
|
||||
{
|
||||
struct thread_sync_data *tsd = (struct thread_sync_data*)arg;
|
||||
struct thread_sync_data *tsd = (struct thread_sync_data *)arg;
|
||||
struct thread_data *td = tsd->td;
|
||||
char service[12];
|
||||
int rc;
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
char buf[1];
|
||||
#endif
|
||||
|
||||
msnprintf(service, sizeof(service), "%d", tsd->port);
|
||||
|
||||
rc = Curl_getaddrinfo_ex(tsd->hostname, service, &tsd->hints, &tsd->res);
|
||||
|
||||
if(rc != 0) {
|
||||
if(rc) {
|
||||
tsd->sock_error = SOCKERRNO?SOCKERRNO:rc;
|
||||
if(tsd->sock_error == 0)
|
||||
tsd->sock_error = RESOLVER_ENOMEM;
|
||||
|
@ -298,6 +316,16 @@ static unsigned int CURL_STDCALL getaddrinfo_thread(void *arg)
|
|||
free(td);
|
||||
}
|
||||
else {
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
if(tsd->sock_pair[1] != CURL_SOCKET_BAD) {
|
||||
/* DNS has been resolved, signal client task */
|
||||
buf[0] = 1;
|
||||
if(swrite(tsd->sock_pair[1], buf, sizeof(buf)) < 0) {
|
||||
/* update sock_erro to errno */
|
||||
tsd->sock_error = SOCKERRNO;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
tsd->done = 1;
|
||||
Curl_mutex_release(tsd->mtx);
|
||||
}
|
||||
|
@ -345,9 +373,13 @@ static unsigned int CURL_STDCALL gethostbyname_thread(void *arg)
|
|||
*/
|
||||
static void destroy_async_data(struct Curl_async *async)
|
||||
{
|
||||
if(async->os_specific) {
|
||||
struct thread_data *td = (struct thread_data*) async->os_specific;
|
||||
if(async->tdata) {
|
||||
struct thread_data *td = async->tdata;
|
||||
int done;
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
curl_socket_t sock_rd = td->tsd.sock_pair[0];
|
||||
struct Curl_easy *data = td->tsd.data;
|
||||
#endif
|
||||
|
||||
/*
|
||||
* if the thread is still blocking in the resolve syscall, detach it and
|
||||
|
@ -367,10 +399,18 @@ static void destroy_async_data(struct Curl_async *async)
|
|||
|
||||
destroy_thread_sync_data(&td->tsd);
|
||||
|
||||
free(async->os_specific);
|
||||
free(async->tdata);
|
||||
}
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
/*
|
||||
* ensure CURLMOPT_SOCKETFUNCTION fires CURL_POLL_REMOVE
|
||||
* before the FD is invalidated to avoid EBADF on EPOLL_CTL_DEL
|
||||
*/
|
||||
Curl_multi_closed(data, sock_rd);
|
||||
sclose(sock_rd);
|
||||
#endif
|
||||
}
|
||||
async->os_specific = NULL;
|
||||
async->tdata = NULL;
|
||||
|
||||
free(async->hostname);
|
||||
async->hostname = NULL;
|
||||
|
@ -382,32 +422,33 @@ static void destroy_async_data(struct Curl_async *async)
|
|||
*
|
||||
* Returns FALSE in case of failure, otherwise TRUE.
|
||||
*/
|
||||
static bool init_resolve_thread(struct connectdata *conn,
|
||||
static bool init_resolve_thread(struct Curl_easy *data,
|
||||
const char *hostname, int port,
|
||||
const struct addrinfo *hints)
|
||||
{
|
||||
struct thread_data *td = calloc(1, sizeof(struct thread_data));
|
||||
int err = ENOMEM;
|
||||
struct Curl_async *asp = &data->state.async;
|
||||
|
||||
conn->async.os_specific = (void *)td;
|
||||
data->state.async.tdata = td;
|
||||
if(!td)
|
||||
goto errno_exit;
|
||||
|
||||
conn->async.port = port;
|
||||
conn->async.done = FALSE;
|
||||
conn->async.status = 0;
|
||||
conn->async.dns = NULL;
|
||||
asp->port = port;
|
||||
asp->done = FALSE;
|
||||
asp->status = 0;
|
||||
asp->dns = NULL;
|
||||
td->thread_hnd = curl_thread_t_null;
|
||||
|
||||
if(!init_thread_sync_data(td, hostname, port, hints)) {
|
||||
conn->async.os_specific = NULL;
|
||||
asp->tdata = NULL;
|
||||
free(td);
|
||||
goto errno_exit;
|
||||
}
|
||||
|
||||
free(conn->async.hostname);
|
||||
conn->async.hostname = strdup(hostname);
|
||||
if(!conn->async.hostname)
|
||||
free(asp->hostname);
|
||||
asp->hostname = strdup(hostname);
|
||||
if(!asp->hostname)
|
||||
goto err_exit;
|
||||
|
||||
/* The thread will set this to 1 when complete. */
|
||||
|
@ -429,7 +470,7 @@ static bool init_resolve_thread(struct connectdata *conn,
|
|||
return TRUE;
|
||||
|
||||
err_exit:
|
||||
destroy_async_data(&conn->async);
|
||||
destroy_async_data(asp);
|
||||
|
||||
errno_exit:
|
||||
errno = err;
|
||||
|
@ -437,61 +478,41 @@ static bool init_resolve_thread(struct connectdata *conn,
|
|||
}
|
||||
|
||||
/*
|
||||
* resolver_error() calls failf() with the appropriate message after a resolve
|
||||
* error
|
||||
* 'entry' may be NULL and then no data is returned
|
||||
*/
|
||||
|
||||
static CURLcode resolver_error(struct connectdata *conn)
|
||||
{
|
||||
const char *host_or_proxy;
|
||||
CURLcode result;
|
||||
|
||||
if(conn->bits.httpproxy) {
|
||||
host_or_proxy = "proxy";
|
||||
result = CURLE_COULDNT_RESOLVE_PROXY;
|
||||
}
|
||||
else {
|
||||
host_or_proxy = "host";
|
||||
result = CURLE_COULDNT_RESOLVE_HOST;
|
||||
}
|
||||
|
||||
failf(conn->data, "Could not resolve %s: %s", host_or_proxy,
|
||||
conn->async.hostname);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static CURLcode thread_wait_resolv(struct connectdata *conn,
|
||||
static CURLcode thread_wait_resolv(struct Curl_easy *data,
|
||||
struct Curl_dns_entry **entry,
|
||||
bool report)
|
||||
{
|
||||
struct thread_data *td = (struct thread_data*) conn->async.os_specific;
|
||||
struct thread_data *td;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
DEBUGASSERT(conn && td);
|
||||
DEBUGASSERT(data);
|
||||
td = data->state.async.tdata;
|
||||
DEBUGASSERT(td);
|
||||
DEBUGASSERT(td->thread_hnd != curl_thread_t_null);
|
||||
|
||||
/* wait for the thread to resolve the name */
|
||||
if(Curl_thread_join(&td->thread_hnd)) {
|
||||
if(entry)
|
||||
result = getaddrinfo_complete(conn);
|
||||
result = getaddrinfo_complete(data);
|
||||
}
|
||||
else
|
||||
DEBUGASSERT(0);
|
||||
|
||||
conn->async.done = TRUE;
|
||||
data->state.async.done = TRUE;
|
||||
|
||||
if(entry)
|
||||
*entry = conn->async.dns;
|
||||
*entry = data->state.async.dns;
|
||||
|
||||
if(!conn->async.dns && report)
|
||||
if(!data->state.async.dns && report)
|
||||
/* a name was not resolved, report error */
|
||||
result = resolver_error(conn);
|
||||
result = Curl_resolver_error(data);
|
||||
|
||||
destroy_async_data(&conn->async);
|
||||
destroy_async_data(&data->state.async);
|
||||
|
||||
if(!conn->async.dns && report)
|
||||
connclose(conn, "asynch resolve failed");
|
||||
if(!data->state.async.dns && report)
|
||||
connclose(data->conn, "asynch resolve failed");
|
||||
|
||||
return result;
|
||||
}
|
||||
|
@ -501,17 +522,18 @@ static CURLcode thread_wait_resolv(struct connectdata *conn,
|
|||
* Until we gain a way to signal the resolver threads to stop early, we must
|
||||
* simply wait for them and ignore their results.
|
||||
*/
|
||||
void Curl_resolver_kill(struct connectdata *conn)
|
||||
void Curl_resolver_kill(struct Curl_easy *data)
|
||||
{
|
||||
struct thread_data *td = (struct thread_data*) conn->async.os_specific;
|
||||
struct thread_data *td = data->state.async.tdata;
|
||||
|
||||
/* If we're still resolving, we must wait for the threads to fully clean up,
|
||||
unfortunately. Otherwise, we can simply cancel to clean up any resolver
|
||||
data. */
|
||||
if(td && td->thread_hnd != curl_thread_t_null)
|
||||
(void)thread_wait_resolv(conn, NULL, FALSE);
|
||||
if(td && td->thread_hnd != curl_thread_t_null
|
||||
&& (data->set.quick_exit != 1L))
|
||||
(void)thread_wait_resolv(data, NULL, FALSE);
|
||||
else
|
||||
Curl_resolver_cancel(conn);
|
||||
Curl_resolver_cancel(data);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -527,10 +549,10 @@ void Curl_resolver_kill(struct connectdata *conn)
|
|||
*
|
||||
* This is the version for resolves-in-a-thread.
|
||||
*/
|
||||
CURLcode Curl_resolver_wait_resolv(struct connectdata *conn,
|
||||
CURLcode Curl_resolver_wait_resolv(struct Curl_easy *data,
|
||||
struct Curl_dns_entry **entry)
|
||||
{
|
||||
return thread_wait_resolv(conn, entry, TRUE);
|
||||
return thread_wait_resolv(data, entry, TRUE);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -538,13 +560,13 @@ CURLcode Curl_resolver_wait_resolv(struct connectdata *conn,
|
|||
* name resolve request has completed. It should also make sure to time-out if
|
||||
* the operation seems to take too long.
|
||||
*/
|
||||
CURLcode Curl_resolver_is_resolved(struct connectdata *conn,
|
||||
CURLcode Curl_resolver_is_resolved(struct Curl_easy *data,
|
||||
struct Curl_dns_entry **entry)
|
||||
{
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct thread_data *td = (struct thread_data*) conn->async.os_specific;
|
||||
struct thread_data *td = data->state.async.tdata;
|
||||
int done = 0;
|
||||
|
||||
DEBUGASSERT(entry);
|
||||
*entry = NULL;
|
||||
|
||||
if(!td) {
|
||||
|
@ -557,18 +579,19 @@ CURLcode Curl_resolver_is_resolved(struct connectdata *conn,
|
|||
Curl_mutex_release(td->tsd.mtx);
|
||||
|
||||
if(done) {
|
||||
getaddrinfo_complete(conn);
|
||||
getaddrinfo_complete(data);
|
||||
|
||||
if(!conn->async.dns) {
|
||||
CURLcode result = resolver_error(conn);
|
||||
destroy_async_data(&conn->async);
|
||||
if(!data->state.async.dns) {
|
||||
CURLcode result = Curl_resolver_error(data);
|
||||
destroy_async_data(&data->state.async);
|
||||
return result;
|
||||
}
|
||||
destroy_async_data(&conn->async);
|
||||
*entry = conn->async.dns;
|
||||
destroy_async_data(&data->state.async);
|
||||
*entry = data->state.async.dns;
|
||||
}
|
||||
else {
|
||||
/* poll for name lookup done with exponential backoff up to 250ms */
|
||||
/* should be fine even if this converts to 32 bit */
|
||||
timediff_t elapsed = Curl_timediff(Curl_now(),
|
||||
data->progress.t_startsingle);
|
||||
if(elapsed < 0)
|
||||
|
@ -585,63 +608,73 @@ CURLcode Curl_resolver_is_resolved(struct connectdata *conn,
|
|||
td->poll_interval = 250;
|
||||
|
||||
td->interval_end = elapsed + td->poll_interval;
|
||||
Curl_expire(conn->data, td->poll_interval, EXPIRE_ASYNC_NAME);
|
||||
Curl_expire(data, td->poll_interval, EXPIRE_ASYNC_NAME);
|
||||
}
|
||||
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
int Curl_resolver_getsock(struct connectdata *conn,
|
||||
curl_socket_t *socks,
|
||||
int numsocks)
|
||||
int Curl_resolver_getsock(struct Curl_easy *data, curl_socket_t *socks)
|
||||
{
|
||||
time_t milli;
|
||||
int ret_val = 0;
|
||||
timediff_t milli;
|
||||
timediff_t ms;
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct resdata *reslv = (struct resdata *)data->state.resolver;
|
||||
struct resdata *reslv = (struct resdata *)data->state.async.resolver;
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
struct thread_data *td = data->state.async.tdata;
|
||||
#else
|
||||
(void)socks;
|
||||
(void)numsocks;
|
||||
ms = Curl_timediff(Curl_now(), reslv->start);
|
||||
if(ms < 3)
|
||||
milli = 0;
|
||||
else if(ms <= 50)
|
||||
milli = ms/3;
|
||||
else if(ms <= 250)
|
||||
milli = 50;
|
||||
else
|
||||
milli = 200;
|
||||
Curl_expire(data, milli, EXPIRE_ASYNC_NAME);
|
||||
return 0;
|
||||
#endif
|
||||
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
if(td) {
|
||||
/* return read fd to client for polling the DNS resolution status */
|
||||
socks[0] = td->tsd.sock_pair[0];
|
||||
td->tsd.data = data;
|
||||
ret_val = GETSOCK_READSOCK(0);
|
||||
}
|
||||
else {
|
||||
#endif
|
||||
ms = Curl_timediff(Curl_now(), reslv->start);
|
||||
if(ms < 3)
|
||||
milli = 0;
|
||||
else if(ms <= 50)
|
||||
milli = ms/3;
|
||||
else if(ms <= 250)
|
||||
milli = 50;
|
||||
else
|
||||
milli = 200;
|
||||
Curl_expire(data, milli, EXPIRE_ASYNC_NAME);
|
||||
#ifndef CURL_DISABLE_SOCKETPAIR
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
return ret_val;
|
||||
}
|
||||
|
||||
#ifndef HAVE_GETADDRINFO
|
||||
/*
|
||||
* Curl_getaddrinfo() - for platforms without getaddrinfo
|
||||
*/
|
||||
Curl_addrinfo *Curl_resolver_getaddrinfo(struct connectdata *conn,
|
||||
const char *hostname,
|
||||
int port,
|
||||
int *waitp)
|
||||
struct Curl_addrinfo *Curl_resolver_getaddrinfo(struct Curl_easy *data,
|
||||
const char *hostname,
|
||||
int port,
|
||||
int *waitp)
|
||||
{
|
||||
struct in_addr in;
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct resdata *reslv = (struct resdata *)data->state.resolver;
|
||||
struct resdata *reslv = (struct resdata *)data->state.async.resolver;
|
||||
|
||||
*waitp = 0; /* default to synchronous response */
|
||||
|
||||
if(Curl_inet_pton(AF_INET, hostname, &in) > 0)
|
||||
/* This is a dotted IP address 123.123.123.123-style */
|
||||
return Curl_ip2addr(AF_INET, &in, hostname, port);
|
||||
|
||||
reslv->start = Curl_now();
|
||||
|
||||
/* fire up a new resolver thread! */
|
||||
if(init_resolve_thread(conn, hostname, port, NULL)) {
|
||||
if(init_resolve_thread(data, hostname, port, NULL)) {
|
||||
*waitp = 1; /* expect asynchronous response */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
failf(conn->data, "getaddrinfo() thread failed\n");
|
||||
failf(data, "getaddrinfo() thread failed");
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
@ -651,73 +684,36 @@ Curl_addrinfo *Curl_resolver_getaddrinfo(struct connectdata *conn,
|
|||
/*
|
||||
* Curl_resolver_getaddrinfo() - for getaddrinfo
|
||||
*/
|
||||
Curl_addrinfo *Curl_resolver_getaddrinfo(struct connectdata *conn,
|
||||
const char *hostname,
|
||||
int port,
|
||||
int *waitp)
|
||||
struct Curl_addrinfo *Curl_resolver_getaddrinfo(struct Curl_easy *data,
|
||||
const char *hostname,
|
||||
int port,
|
||||
int *waitp)
|
||||
{
|
||||
struct addrinfo hints;
|
||||
char sbuf[12];
|
||||
int pf = PF_INET;
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct resdata *reslv = (struct resdata *)data->state.resolver;
|
||||
struct resdata *reslv = (struct resdata *)data->state.async.resolver;
|
||||
|
||||
*waitp = 0; /* default to synchronous response */
|
||||
|
||||
#ifndef USE_RESOLVE_ON_IPS
|
||||
{
|
||||
struct in_addr in;
|
||||
/* First check if this is an IPv4 address string */
|
||||
if(Curl_inet_pton(AF_INET, hostname, &in) > 0)
|
||||
/* This is a dotted IP address 123.123.123.123-style */
|
||||
return Curl_ip2addr(AF_INET, &in, hostname, port);
|
||||
}
|
||||
#ifdef CURLRES_IPV6
|
||||
{
|
||||
struct in6_addr in6;
|
||||
/* check if this is an IPv6 address string */
|
||||
if(Curl_inet_pton(AF_INET6, hostname, &in6) > 0)
|
||||
/* This is an IPv6 address literal */
|
||||
return Curl_ip2addr(AF_INET6, &in6, hostname, port);
|
||||
}
|
||||
#endif /* CURLRES_IPV6 */
|
||||
#endif /* !USE_RESOLVE_ON_IPS */
|
||||
|
||||
#ifdef CURLRES_IPV6
|
||||
/*
|
||||
* Check if a limited name resolve has been requested.
|
||||
*/
|
||||
switch(conn->ip_version) {
|
||||
case CURL_IPRESOLVE_V4:
|
||||
pf = PF_INET;
|
||||
break;
|
||||
case CURL_IPRESOLVE_V6:
|
||||
pf = PF_INET6;
|
||||
break;
|
||||
default:
|
||||
if((data->conn->ip_version != CURL_IPRESOLVE_V4) && Curl_ipv6works(data))
|
||||
/* The stack seems to be IPv6-enabled */
|
||||
pf = PF_UNSPEC;
|
||||
break;
|
||||
}
|
||||
|
||||
if((pf != PF_INET) && !Curl_ipv6works())
|
||||
/* The stack seems to be a non-IPv6 one */
|
||||
pf = PF_INET;
|
||||
#endif /* CURLRES_IPV6 */
|
||||
|
||||
memset(&hints, 0, sizeof(hints));
|
||||
hints.ai_family = pf;
|
||||
hints.ai_socktype = conn->socktype;
|
||||
|
||||
msnprintf(sbuf, sizeof(sbuf), "%d", port);
|
||||
hints.ai_socktype = (data->conn->transport == TRNSPRT_TCP)?
|
||||
SOCK_STREAM : SOCK_DGRAM;
|
||||
|
||||
reslv->start = Curl_now();
|
||||
/* fire up a new resolver thread! */
|
||||
if(init_resolve_thread(conn, hostname, port, &hints)) {
|
||||
if(init_resolve_thread(data, hostname, port, &hints)) {
|
||||
*waitp = 1; /* expect asynchronous response */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
failf(data, "getaddrinfo() thread failed to start\n");
|
||||
failf(data, "getaddrinfo() thread failed to start");
|
||||
return NULL;
|
||||
|
||||
}
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -91,7 +93,7 @@ CURLcode Curl_resolver_duphandle(struct Curl_easy *easy, void **to,
|
|||
*
|
||||
* It is safe to call this when conn is in any state.
|
||||
*/
|
||||
void Curl_resolver_cancel(struct connectdata *conn);
|
||||
void Curl_resolver_cancel(struct Curl_easy *data);
|
||||
|
||||
/*
|
||||
* Curl_resolver_kill().
|
||||
|
@ -104,7 +106,7 @@ void Curl_resolver_cancel(struct connectdata *conn);
|
|||
*
|
||||
* It is safe to call this when conn is in any state.
|
||||
*/
|
||||
void Curl_resolver_kill(struct connectdata *conn);
|
||||
void Curl_resolver_kill(struct Curl_easy *data);
|
||||
|
||||
/* Curl_resolver_getsock()
|
||||
*
|
||||
|
@ -114,8 +116,7 @@ void Curl_resolver_kill(struct connectdata *conn);
|
|||
* return bitmask indicating what file descriptors (referring to array indexes
|
||||
* in the 'sock' array) to wait for, read/write.
|
||||
*/
|
||||
int Curl_resolver_getsock(struct connectdata *conn, curl_socket_t *sock,
|
||||
int numsocks);
|
||||
int Curl_resolver_getsock(struct Curl_easy *data, curl_socket_t *sock);
|
||||
|
||||
/*
|
||||
* Curl_resolver_is_resolved()
|
||||
|
@ -126,7 +127,7 @@ int Curl_resolver_getsock(struct connectdata *conn, curl_socket_t *sock,
|
|||
*
|
||||
* Returns normal CURLcode errors.
|
||||
*/
|
||||
CURLcode Curl_resolver_is_resolved(struct connectdata *conn,
|
||||
CURLcode Curl_resolver_is_resolved(struct Curl_easy *data,
|
||||
struct Curl_dns_entry **dns);
|
||||
|
||||
/*
|
||||
|
@ -140,24 +141,24 @@ CURLcode Curl_resolver_is_resolved(struct connectdata *conn,
|
|||
* Returns CURLE_COULDNT_RESOLVE_HOST if the host was not resolved,
|
||||
* CURLE_OPERATION_TIMEDOUT if a time-out occurred, or other errors.
|
||||
*/
|
||||
CURLcode Curl_resolver_wait_resolv(struct connectdata *conn,
|
||||
CURLcode Curl_resolver_wait_resolv(struct Curl_easy *data,
|
||||
struct Curl_dns_entry **dnsentry);
|
||||
|
||||
/*
|
||||
* Curl_resolver_getaddrinfo() - when using this resolver
|
||||
*
|
||||
* Returns name information about the given hostname and port number. If
|
||||
* successful, the 'hostent' is returned and the forth argument will point to
|
||||
* successful, the 'hostent' is returned and the fourth argument will point to
|
||||
* memory we need to free after use. That memory *MUST* be freed with
|
||||
* Curl_freeaddrinfo(), nothing else.
|
||||
*
|
||||
* Each resolver backend must of course make sure to return data in the
|
||||
* correct format to comply with this.
|
||||
*/
|
||||
Curl_addrinfo *Curl_resolver_getaddrinfo(struct connectdata *conn,
|
||||
const char *hostname,
|
||||
int port,
|
||||
int *waitp);
|
||||
struct Curl_addrinfo *Curl_resolver_getaddrinfo(struct Curl_easy *data,
|
||||
const char *hostname,
|
||||
int port,
|
||||
int *waitp);
|
||||
|
||||
#ifndef CURLRES_ASYNCH
|
||||
/* convert these functions if an asynch resolver isn't used */
|
||||
|
@ -165,7 +166,6 @@ Curl_addrinfo *Curl_resolver_getaddrinfo(struct connectdata *conn,
|
|||
#define Curl_resolver_kill(x) Curl_nop_stmt
|
||||
#define Curl_resolver_is_resolved(x,y) CURLE_COULDNT_RESOLVE_HOST
|
||||
#define Curl_resolver_wait_resolv(x,y) CURLE_COULDNT_RESOLVE_HOST
|
||||
#define Curl_resolver_getsock(x,y,z) 0
|
||||
#define Curl_resolver_duphandle(x,y,z) CURLE_OK
|
||||
#define Curl_resolver_init(x,y) CURLE_OK
|
||||
#define Curl_resolver_global_init() CURLE_OK
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,75 +18,45 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/* Base64 encoding/decoding */
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if !defined(CURL_DISABLE_HTTP_AUTH) || defined(USE_LIBSSH2) || \
|
||||
defined(USE_LIBSSH) || !defined(CURL_DISABLE_LDAP) || \
|
||||
#if !defined(CURL_DISABLE_HTTP_AUTH) || defined(USE_SSH) || \
|
||||
!defined(CURL_DISABLE_LDAP) || \
|
||||
!defined(CURL_DISABLE_SMTP) || \
|
||||
!defined(CURL_DISABLE_POP3) || \
|
||||
!defined(CURL_DISABLE_IMAP) || \
|
||||
!defined(CURL_DISABLE_DOH) || defined(USE_SSL)
|
||||
|
||||
#include "urldata.h" /* for the Curl_easy definition */
|
||||
#include "warnless.h"
|
||||
#include "curl_base64.h"
|
||||
#include "non-ascii.h"
|
||||
|
||||
/* The last 3 #include files should be in this order */
|
||||
#include "curl_printf.h"
|
||||
/* The last 2 #include files should be in this order */
|
||||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
/* ---- Base64 Encoding/Decoding Table --- */
|
||||
/* Padding character string starts at offset 64. */
|
||||
static const char base64[]=
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";
|
||||
|
||||
/* The Base 64 encoding with an URL and filename safe alphabet, RFC 4648
|
||||
/* The Base 64 encoding with a URL and filename safe alphabet, RFC 4648
|
||||
section 5 */
|
||||
static const char base64url[]=
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_";
|
||||
|
||||
static size_t decodeQuantum(unsigned char *dest, const char *src)
|
||||
{
|
||||
size_t padding = 0;
|
||||
const char *s, *p;
|
||||
unsigned long i, x = 0;
|
||||
|
||||
for(i = 0, s = src; i < 4; i++, s++) {
|
||||
if(*s == '=') {
|
||||
x = (x << 6);
|
||||
padding++;
|
||||
}
|
||||
else {
|
||||
unsigned long v = 0;
|
||||
p = base64;
|
||||
|
||||
while(*p && (*p != *s)) {
|
||||
v++;
|
||||
p++;
|
||||
}
|
||||
|
||||
if(*p == *s)
|
||||
x = (x << 6) + v;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
if(padding < 1)
|
||||
dest[2] = curlx_ultouc(x & 0xFFUL);
|
||||
|
||||
x >>= 8;
|
||||
if(padding < 2)
|
||||
dest[1] = curlx_ultouc(x & 0xFFUL);
|
||||
|
||||
x >>= 8;
|
||||
dest[0] = curlx_ultouc(x & 0xFFUL);
|
||||
|
||||
return 3 - padding;
|
||||
}
|
||||
|
||||
static const unsigned char decodetable[] =
|
||||
{ 62, 255, 255, 255, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 255, 255, 255,
|
||||
255, 255, 255, 255, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16,
|
||||
17, 18, 19, 20, 21, 22, 23, 24, 25, 255, 255, 255, 255, 255, 255, 26, 27, 28,
|
||||
29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47,
|
||||
48, 49, 50, 51 };
|
||||
/*
|
||||
* Curl_base64_decode()
|
||||
*
|
||||
|
@ -105,13 +75,14 @@ CURLcode Curl_base64_decode(const char *src,
|
|||
unsigned char **outptr, size_t *outlen)
|
||||
{
|
||||
size_t srclen = 0;
|
||||
size_t length = 0;
|
||||
size_t padding = 0;
|
||||
size_t i;
|
||||
size_t numQuantums;
|
||||
size_t fullQuantums;
|
||||
size_t rawlen = 0;
|
||||
unsigned char *pos;
|
||||
unsigned char *newstr;
|
||||
unsigned char lookup[256];
|
||||
|
||||
*outptr = NULL;
|
||||
*outlen = 0;
|
||||
|
@ -121,45 +92,82 @@ CURLcode Curl_base64_decode(const char *src,
|
|||
if(!srclen || srclen % 4)
|
||||
return CURLE_BAD_CONTENT_ENCODING;
|
||||
|
||||
/* Find the position of any = padding characters */
|
||||
while((src[length] != '=') && src[length])
|
||||
length++;
|
||||
|
||||
/* A maximum of two = padding characters is allowed */
|
||||
if(src[length] == '=') {
|
||||
/* srclen is at least 4 here */
|
||||
while(src[srclen - 1 - padding] == '=') {
|
||||
/* count padding characters */
|
||||
padding++;
|
||||
if(src[length + 1] == '=')
|
||||
padding++;
|
||||
/* A maximum of two = padding characters is allowed */
|
||||
if(padding > 2)
|
||||
return CURLE_BAD_CONTENT_ENCODING;
|
||||
}
|
||||
|
||||
/* Check the = padding characters weren't part way through the input */
|
||||
if(length + padding != srclen)
|
||||
return CURLE_BAD_CONTENT_ENCODING;
|
||||
|
||||
/* Calculate the number of quantums */
|
||||
numQuantums = srclen / 4;
|
||||
fullQuantums = numQuantums - (padding ? 1 : 0);
|
||||
|
||||
/* Calculate the size of the decoded string */
|
||||
rawlen = (numQuantums * 3) - padding;
|
||||
|
||||
/* Allocate our buffer including room for a zero terminator */
|
||||
/* Allocate our buffer including room for a null-terminator */
|
||||
newstr = malloc(rawlen + 1);
|
||||
if(!newstr)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
||||
pos = newstr;
|
||||
|
||||
/* Decode the quantums */
|
||||
for(i = 0; i < numQuantums; i++) {
|
||||
size_t result = decodeQuantum(pos, src);
|
||||
if(!result) {
|
||||
free(newstr);
|
||||
memset(lookup, 0xff, sizeof(lookup));
|
||||
memcpy(&lookup['+'], decodetable, sizeof(decodetable));
|
||||
/* replaces
|
||||
{
|
||||
unsigned char c;
|
||||
const unsigned char *p = (const unsigned char *)base64;
|
||||
for(c = 0; *p; c++, p++)
|
||||
lookup[*p] = c;
|
||||
}
|
||||
*/
|
||||
|
||||
return CURLE_BAD_CONTENT_ENCODING;
|
||||
/* Decode the complete quantums first */
|
||||
for(i = 0; i < fullQuantums; i++) {
|
||||
unsigned char val;
|
||||
unsigned int x = 0;
|
||||
int j;
|
||||
|
||||
for(j = 0; j < 4; j++) {
|
||||
val = lookup[(unsigned char)*src++];
|
||||
if(val == 0xff) /* bad symbol */
|
||||
goto bad;
|
||||
x = (x << 6) | val;
|
||||
}
|
||||
|
||||
pos += result;
|
||||
src += 4;
|
||||
pos[2] = x & 0xff;
|
||||
pos[1] = (x >> 8) & 0xff;
|
||||
pos[0] = (x >> 16) & 0xff;
|
||||
pos += 3;
|
||||
}
|
||||
if(padding) {
|
||||
/* this means either 8 or 16 bits output */
|
||||
unsigned char val;
|
||||
unsigned int x = 0;
|
||||
int j;
|
||||
size_t padc = 0;
|
||||
for(j = 0; j < 4; j++) {
|
||||
if(*src == '=') {
|
||||
x <<= 6;
|
||||
src++;
|
||||
if(++padc > padding)
|
||||
/* this is a badly placed '=' symbol! */
|
||||
goto bad;
|
||||
}
|
||||
else {
|
||||
val = lookup[(unsigned char)*src++];
|
||||
if(val == 0xff) /* bad symbol */
|
||||
goto bad;
|
||||
x = (x << 6) | val;
|
||||
}
|
||||
}
|
||||
if(padding == 1)
|
||||
pos[1] = (x >> 8) & 0xff;
|
||||
pos[0] = (x >> 16) & 0xff;
|
||||
pos += 3 - padding;
|
||||
}
|
||||
|
||||
/* Zero terminate */
|
||||
|
@ -170,95 +178,60 @@ CURLcode Curl_base64_decode(const char *src,
|
|||
*outlen = rawlen;
|
||||
|
||||
return CURLE_OK;
|
||||
bad:
|
||||
free(newstr);
|
||||
return CURLE_BAD_CONTENT_ENCODING;
|
||||
}
|
||||
|
||||
static CURLcode base64_encode(const char *table64,
|
||||
struct Curl_easy *data,
|
||||
const char *inputbuff, size_t insize,
|
||||
char **outptr, size_t *outlen)
|
||||
{
|
||||
CURLcode result;
|
||||
unsigned char ibuf[3];
|
||||
unsigned char obuf[4];
|
||||
int i;
|
||||
int inputparts;
|
||||
char *output;
|
||||
char *base64data;
|
||||
char *convbuf = NULL;
|
||||
|
||||
const char *indata = inputbuff;
|
||||
const unsigned char *in = (unsigned char *)inputbuff;
|
||||
const char *padstr = &table64[64]; /* Point to padding string. */
|
||||
|
||||
*outptr = NULL;
|
||||
*outlen = 0;
|
||||
|
||||
if(!insize)
|
||||
insize = strlen(indata);
|
||||
insize = strlen(inputbuff);
|
||||
|
||||
#if SIZEOF_SIZE_T == 4
|
||||
if(insize > UINT_MAX/4)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
#endif
|
||||
|
||||
base64data = output = malloc(insize * 4 / 3 + 4);
|
||||
base64data = output = malloc((insize + 2) / 3 * 4 + 1);
|
||||
if(!output)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
||||
/*
|
||||
* The base64 data needs to be created using the network encoding
|
||||
* not the host encoding. And we can't change the actual input
|
||||
* so we copy it to a buffer, translate it, and use that instead.
|
||||
*/
|
||||
result = Curl_convert_clone(data, indata, insize, &convbuf);
|
||||
if(result) {
|
||||
free(output);
|
||||
return result;
|
||||
while(insize >= 3) {
|
||||
*output++ = table64[ in[0] >> 2 ];
|
||||
*output++ = table64[ ((in[0] & 0x03) << 4) | (in[1] >> 4) ];
|
||||
*output++ = table64[ ((in[1] & 0x0F) << 2) | ((in[2] & 0xC0) >> 6) ];
|
||||
*output++ = table64[ in[2] & 0x3F ];
|
||||
insize -= 3;
|
||||
in += 3;
|
||||
}
|
||||
|
||||
if(convbuf)
|
||||
indata = (char *)convbuf;
|
||||
|
||||
while(insize > 0) {
|
||||
for(i = inputparts = 0; i < 3; i++) {
|
||||
if(insize > 0) {
|
||||
inputparts++;
|
||||
ibuf[i] = (unsigned char) *indata;
|
||||
indata++;
|
||||
insize--;
|
||||
if(insize) {
|
||||
/* this is only one or two bytes now */
|
||||
*output++ = table64[ in[0] >> 2 ];
|
||||
if(insize == 1) {
|
||||
*output++ = table64[ ((in[0] & 0x03) << 4) ];
|
||||
if(*padstr) {
|
||||
*output++ = *padstr;
|
||||
*output++ = *padstr;
|
||||
}
|
||||
else
|
||||
ibuf[i] = 0;
|
||||
}
|
||||
|
||||
obuf[0] = (unsigned char) ((ibuf[0] & 0xFC) >> 2);
|
||||
obuf[1] = (unsigned char) (((ibuf[0] & 0x03) << 4) | \
|
||||
((ibuf[1] & 0xF0) >> 4));
|
||||
obuf[2] = (unsigned char) (((ibuf[1] & 0x0F) << 2) | \
|
||||
((ibuf[2] & 0xC0) >> 6));
|
||||
obuf[3] = (unsigned char) (ibuf[2] & 0x3F);
|
||||
|
||||
switch(inputparts) {
|
||||
case 1: /* only one byte read */
|
||||
msnprintf(output, 5, "%c%c==",
|
||||
table64[obuf[0]],
|
||||
table64[obuf[1]]);
|
||||
break;
|
||||
|
||||
case 2: /* two bytes read */
|
||||
msnprintf(output, 5, "%c%c%c=",
|
||||
table64[obuf[0]],
|
||||
table64[obuf[1]],
|
||||
table64[obuf[2]]);
|
||||
break;
|
||||
|
||||
default:
|
||||
msnprintf(output, 5, "%c%c%c%c",
|
||||
table64[obuf[0]],
|
||||
table64[obuf[1]],
|
||||
table64[obuf[2]],
|
||||
table64[obuf[3]]);
|
||||
break;
|
||||
else {
|
||||
/* insize == 2 */
|
||||
*output++ = table64[ ((in[0] & 0x03) << 4) | ((in[1] & 0xF0) >> 4) ];
|
||||
*output++ = table64[ ((in[1] & 0x0F) << 2) ];
|
||||
if(*padstr)
|
||||
*output++ = *padstr;
|
||||
}
|
||||
output += 4;
|
||||
}
|
||||
|
||||
/* Zero terminate */
|
||||
|
@ -267,10 +240,8 @@ static CURLcode base64_encode(const char *table64,
|
|||
/* Return the pointer to the new data (allocated memory) */
|
||||
*outptr = base64data;
|
||||
|
||||
free(convbuf);
|
||||
|
||||
/* Return the length of the new data */
|
||||
*outlen = strlen(base64data);
|
||||
*outlen = output - base64data;
|
||||
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
@ -288,15 +259,12 @@ static CURLcode base64_encode(const char *table64,
|
|||
* Returns CURLE_OK on success, otherwise specific error code. Function
|
||||
* output shall not be considered valid unless CURLE_OK is returned.
|
||||
*
|
||||
* When encoded data length is 0, returns NULL in *outptr.
|
||||
*
|
||||
* @unittest: 1302
|
||||
*/
|
||||
CURLcode Curl_base64_encode(struct Curl_easy *data,
|
||||
const char *inputbuff, size_t insize,
|
||||
CURLcode Curl_base64_encode(const char *inputbuff, size_t insize,
|
||||
char **outptr, size_t *outlen)
|
||||
{
|
||||
return base64_encode(base64, data, inputbuff, insize, outptr, outlen);
|
||||
return base64_encode(base64, inputbuff, insize, outptr, outlen);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -312,15 +280,12 @@ CURLcode Curl_base64_encode(struct Curl_easy *data,
|
|||
* Returns CURLE_OK on success, otherwise specific error code. Function
|
||||
* output shall not be considered valid unless CURLE_OK is returned.
|
||||
*
|
||||
* When encoded data length is 0, returns NULL in *outptr.
|
||||
*
|
||||
* @unittest: 1302
|
||||
*/
|
||||
CURLcode Curl_base64url_encode(struct Curl_easy *data,
|
||||
const char *inputbuff, size_t insize,
|
||||
CURLcode Curl_base64url_encode(const char *inputbuff, size_t insize,
|
||||
char **outptr, size_t *outlen)
|
||||
{
|
||||
return base64_encode(base64url, data, inputbuff, insize, outptr, outlen);
|
||||
return base64_encode(base64url, inputbuff, insize, outptr, outlen);
|
||||
}
|
||||
|
||||
#endif /* no users so disabled */
|
||||
|
|
129
src/dependencies/cmcurl/lib/bufref.c
Normal file
129
src/dependencies/cmcurl/lib/bufref.c
Normal file
|
@ -0,0 +1,129 @@
|
|||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
#include "urldata.h"
|
||||
#include "bufref.h"
|
||||
|
||||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
#define SIGNATURE 0x5c48e9b2 /* Random pattern. */
|
||||
|
||||
/*
|
||||
* Init a bufref struct.
|
||||
*/
|
||||
void Curl_bufref_init(struct bufref *br)
|
||||
{
|
||||
DEBUGASSERT(br);
|
||||
br->dtor = NULL;
|
||||
br->ptr = NULL;
|
||||
br->len = 0;
|
||||
|
||||
#ifdef DEBUGBUILD
|
||||
br->signature = SIGNATURE;
|
||||
#endif
|
||||
}
|
||||
|
||||
/*
|
||||
* Free the buffer and re-init the necessary fields. It doesn't touch the
|
||||
* 'signature' field and thus this buffer reference can be reused.
|
||||
*/
|
||||
|
||||
void Curl_bufref_free(struct bufref *br)
|
||||
{
|
||||
DEBUGASSERT(br);
|
||||
DEBUGASSERT(br->signature == SIGNATURE);
|
||||
DEBUGASSERT(br->ptr || !br->len);
|
||||
|
||||
if(br->ptr && br->dtor)
|
||||
br->dtor((void *) br->ptr);
|
||||
|
||||
br->dtor = NULL;
|
||||
br->ptr = NULL;
|
||||
br->len = 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Set the buffer reference to new values. The previously referenced buffer
|
||||
* is released before assignment.
|
||||
*/
|
||||
void Curl_bufref_set(struct bufref *br, const void *ptr, size_t len,
|
||||
void (*dtor)(void *))
|
||||
{
|
||||
DEBUGASSERT(ptr || !len);
|
||||
DEBUGASSERT(len <= CURL_MAX_INPUT_LENGTH);
|
||||
|
||||
Curl_bufref_free(br);
|
||||
br->ptr = (const unsigned char *) ptr;
|
||||
br->len = len;
|
||||
br->dtor = dtor;
|
||||
}
|
||||
|
||||
/*
|
||||
* Get a pointer to the referenced buffer.
|
||||
*/
|
||||
const unsigned char *Curl_bufref_ptr(const struct bufref *br)
|
||||
{
|
||||
DEBUGASSERT(br);
|
||||
DEBUGASSERT(br->signature == SIGNATURE);
|
||||
DEBUGASSERT(br->ptr || !br->len);
|
||||
|
||||
return br->ptr;
|
||||
}
|
||||
|
||||
/*
|
||||
* Get the length of the referenced buffer data.
|
||||
*/
|
||||
size_t Curl_bufref_len(const struct bufref *br)
|
||||
{
|
||||
DEBUGASSERT(br);
|
||||
DEBUGASSERT(br->signature == SIGNATURE);
|
||||
DEBUGASSERT(br->ptr || !br->len);
|
||||
|
||||
return br->len;
|
||||
}
|
||||
|
||||
CURLcode Curl_bufref_memdup(struct bufref *br, const void *ptr, size_t len)
|
||||
{
|
||||
unsigned char *cpy = NULL;
|
||||
|
||||
DEBUGASSERT(br);
|
||||
DEBUGASSERT(br->signature == SIGNATURE);
|
||||
DEBUGASSERT(br->ptr || !br->len);
|
||||
DEBUGASSERT(ptr || !len);
|
||||
DEBUGASSERT(len <= CURL_MAX_INPUT_LENGTH);
|
||||
|
||||
if(ptr) {
|
||||
cpy = malloc(len + 1);
|
||||
if(!cpy)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
if(len)
|
||||
memcpy(cpy, ptr, len);
|
||||
cpy[len] = '\0';
|
||||
}
|
||||
|
||||
Curl_bufref_set(br, cpy, len, curl_free);
|
||||
return CURLE_OK;
|
||||
}
|
48
src/dependencies/cmcurl/lib/bufref.h
Normal file
48
src/dependencies/cmcurl/lib/bufref.h
Normal file
|
@ -0,0 +1,48 @@
|
|||
#ifndef HEADER_CURL_BUFREF_H
|
||||
#define HEADER_CURL_BUFREF_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/*
|
||||
* Generic buffer reference.
|
||||
*/
|
||||
struct bufref {
|
||||
void (*dtor)(void *); /* Associated destructor. */
|
||||
const unsigned char *ptr; /* Referenced data buffer. */
|
||||
size_t len; /* The data size in bytes. */
|
||||
#ifdef DEBUGBUILD
|
||||
int signature; /* Detect API use mistakes. */
|
||||
#endif
|
||||
};
|
||||
|
||||
|
||||
void Curl_bufref_init(struct bufref *br);
|
||||
void Curl_bufref_set(struct bufref *br, const void *ptr, size_t len,
|
||||
void (*dtor)(void *));
|
||||
const unsigned char *Curl_bufref_ptr(const struct bufref *br);
|
||||
size_t Curl_bufref_len(const struct bufref *br);
|
||||
CURLcode Curl_bufref_memdup(struct bufref *br, const void *ptr, size_t len);
|
||||
void Curl_bufref_free(struct bufref *br);
|
||||
|
||||
#endif
|
1250
src/dependencies/cmcurl/lib/c-hyper.c
Normal file
1250
src/dependencies/cmcurl/lib/c-hyper.c
Normal file
File diff suppressed because it is too large
Load diff
60
src/dependencies/cmcurl/lib/c-hyper.h
Normal file
60
src/dependencies/cmcurl/lib/c-hyper.h
Normal file
|
@ -0,0 +1,60 @@
|
|||
#ifndef HEADER_CURL_HYPER_H
|
||||
#define HEADER_CURL_HYPER_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if !defined(CURL_DISABLE_HTTP) && defined(USE_HYPER)
|
||||
|
||||
#include <hyper.h>
|
||||
|
||||
/* per-transfer data for the Hyper backend */
|
||||
struct hyptransfer {
|
||||
hyper_waker *write_waker;
|
||||
hyper_waker *read_waker;
|
||||
const hyper_executor *exec;
|
||||
hyper_task *endtask;
|
||||
hyper_waker *exp100_waker;
|
||||
hyper_waker *send_body_waker;
|
||||
};
|
||||
|
||||
size_t Curl_hyper_recv(void *userp, hyper_context *ctx,
|
||||
uint8_t *buf, size_t buflen);
|
||||
size_t Curl_hyper_send(void *userp, hyper_context *ctx,
|
||||
const uint8_t *buf, size_t buflen);
|
||||
CURLcode Curl_hyper_stream(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int *didwhat,
|
||||
bool *done,
|
||||
int select_res);
|
||||
|
||||
CURLcode Curl_hyper_header(struct Curl_easy *data, hyper_headers *headers,
|
||||
const char *line);
|
||||
void Curl_hyper_done(struct Curl_easy *);
|
||||
|
||||
#else
|
||||
#define Curl_hyper_done(x)
|
||||
|
||||
#endif /* !defined(CURL_DISABLE_HTTP) && defined(USE_HYPER) */
|
||||
#endif /* HEADER_CURL_HYPER_H */
|
569
src/dependencies/cmcurl/lib/cf-https-connect.c
Normal file
569
src/dependencies/cmcurl/lib/cf-https-connect.c
Normal file
|
@ -0,0 +1,569 @@
|
|||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if !defined(CURL_DISABLE_HTTP) && !defined(USE_HYPER)
|
||||
|
||||
#include "urldata.h"
|
||||
#include <curl/curl.h>
|
||||
#include "curl_log.h"
|
||||
#include "cfilters.h"
|
||||
#include "connect.h"
|
||||
#include "multiif.h"
|
||||
#include "cf-https-connect.h"
|
||||
#include "http2.h"
|
||||
#include "vquic/vquic.h"
|
||||
|
||||
/* The last 3 #include files should be in this order */
|
||||
#include "curl_printf.h"
|
||||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
|
||||
typedef enum {
|
||||
CF_HC_INIT,
|
||||
CF_HC_CONNECT,
|
||||
CF_HC_SUCCESS,
|
||||
CF_HC_FAILURE
|
||||
} cf_hc_state;
|
||||
|
||||
struct cf_hc_baller {
|
||||
const char *name;
|
||||
struct Curl_cfilter *cf;
|
||||
CURLcode result;
|
||||
struct curltime started;
|
||||
int reply_ms;
|
||||
bool enabled;
|
||||
};
|
||||
|
||||
static void cf_hc_baller_reset(struct cf_hc_baller *b,
|
||||
struct Curl_easy *data)
|
||||
{
|
||||
if(b->cf) {
|
||||
Curl_conn_cf_close(b->cf, data);
|
||||
Curl_conn_cf_discard_chain(&b->cf, data);
|
||||
b->cf = NULL;
|
||||
}
|
||||
b->result = CURLE_OK;
|
||||
b->reply_ms = -1;
|
||||
}
|
||||
|
||||
static bool cf_hc_baller_is_active(struct cf_hc_baller *b)
|
||||
{
|
||||
return b->enabled && b->cf && !b->result;
|
||||
}
|
||||
|
||||
static bool cf_hc_baller_has_started(struct cf_hc_baller *b)
|
||||
{
|
||||
return !!b->cf;
|
||||
}
|
||||
|
||||
static int cf_hc_baller_reply_ms(struct cf_hc_baller *b,
|
||||
struct Curl_easy *data)
|
||||
{
|
||||
if(b->reply_ms < 0)
|
||||
b->cf->cft->query(b->cf, data, CF_QUERY_CONNECT_REPLY_MS,
|
||||
&b->reply_ms, NULL);
|
||||
return b->reply_ms;
|
||||
}
|
||||
|
||||
static bool cf_hc_baller_data_pending(struct cf_hc_baller *b,
|
||||
const struct Curl_easy *data)
|
||||
{
|
||||
return b->cf && !b->result && b->cf->cft->has_data_pending(b->cf, data);
|
||||
}
|
||||
|
||||
struct cf_hc_ctx {
|
||||
cf_hc_state state;
|
||||
const struct Curl_dns_entry *remotehost;
|
||||
struct curltime started; /* when connect started */
|
||||
CURLcode result; /* overall result */
|
||||
struct cf_hc_baller h3_baller;
|
||||
struct cf_hc_baller h21_baller;
|
||||
int soft_eyeballs_timeout_ms;
|
||||
int hard_eyeballs_timeout_ms;
|
||||
};
|
||||
|
||||
static void cf_hc_baller_init(struct cf_hc_baller *b,
|
||||
struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
const char *name,
|
||||
int transport)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
struct Curl_cfilter *save = cf->next;
|
||||
|
||||
b->name = name;
|
||||
cf->next = NULL;
|
||||
b->started = Curl_now();
|
||||
b->result = Curl_cf_setup_insert_after(cf, data, ctx->remotehost,
|
||||
transport, CURL_CF_SSL_ENABLE);
|
||||
b->cf = cf->next;
|
||||
cf->next = save;
|
||||
}
|
||||
|
||||
static CURLcode cf_hc_baller_connect(struct cf_hc_baller *b,
|
||||
struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool *done)
|
||||
{
|
||||
struct Curl_cfilter *save = cf->next;
|
||||
|
||||
cf->next = b->cf;
|
||||
b->result = Curl_conn_cf_connect(cf->next, data, FALSE, done);
|
||||
b->cf = cf->next; /* it might mutate */
|
||||
cf->next = save;
|
||||
return b->result;
|
||||
}
|
||||
|
||||
static void cf_hc_reset(struct Curl_cfilter *cf, struct Curl_easy *data)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
|
||||
if(ctx) {
|
||||
cf_hc_baller_reset(&ctx->h3_baller, data);
|
||||
cf_hc_baller_reset(&ctx->h21_baller, data);
|
||||
ctx->state = CF_HC_INIT;
|
||||
ctx->result = CURLE_OK;
|
||||
ctx->hard_eyeballs_timeout_ms = data->set.happy_eyeballs_timeout;
|
||||
ctx->soft_eyeballs_timeout_ms = data->set.happy_eyeballs_timeout / 2;
|
||||
}
|
||||
}
|
||||
|
||||
static CURLcode baller_connected(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
struct cf_hc_baller *winner)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
DEBUGASSERT(winner->cf);
|
||||
if(winner != &ctx->h3_baller)
|
||||
cf_hc_baller_reset(&ctx->h3_baller, data);
|
||||
if(winner != &ctx->h21_baller)
|
||||
cf_hc_baller_reset(&ctx->h21_baller, data);
|
||||
|
||||
DEBUGF(LOG_CF(data, cf, "connect+handshake %s: %dms, 1st data: %dms",
|
||||
winner->name, (int)Curl_timediff(Curl_now(), winner->started),
|
||||
cf_hc_baller_reply_ms(winner, data)));
|
||||
cf->next = winner->cf;
|
||||
winner->cf = NULL;
|
||||
|
||||
switch(cf->conn->alpn) {
|
||||
case CURL_HTTP_VERSION_3:
|
||||
infof(data, "using HTTP/3");
|
||||
break;
|
||||
case CURL_HTTP_VERSION_2:
|
||||
#ifdef USE_NGHTTP2
|
||||
/* Using nghttp2, we add the filter "below" us, so when the conn
|
||||
* closes, we tear it down for a fresh reconnect */
|
||||
result = Curl_http2_switch_at(cf, data);
|
||||
if(result) {
|
||||
ctx->state = CF_HC_FAILURE;
|
||||
ctx->result = result;
|
||||
return result;
|
||||
}
|
||||
#endif
|
||||
infof(data, "using HTTP/2");
|
||||
break;
|
||||
case CURL_HTTP_VERSION_1_1:
|
||||
infof(data, "using HTTP/1.1");
|
||||
break;
|
||||
default:
|
||||
infof(data, "using HTTP/1.x");
|
||||
break;
|
||||
}
|
||||
ctx->state = CF_HC_SUCCESS;
|
||||
cf->connected = TRUE;
|
||||
Curl_conn_cf_cntrl(cf->next, data, TRUE,
|
||||
CF_CTRL_CONN_INFO_UPDATE, 0, NULL);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
static bool time_to_start_h21(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
struct curltime now)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
timediff_t elapsed_ms;
|
||||
|
||||
if(!ctx->h21_baller.enabled || cf_hc_baller_has_started(&ctx->h21_baller))
|
||||
return FALSE;
|
||||
|
||||
if(!ctx->h3_baller.enabled || !cf_hc_baller_is_active(&ctx->h3_baller))
|
||||
return TRUE;
|
||||
|
||||
elapsed_ms = Curl_timediff(now, ctx->started);
|
||||
if(elapsed_ms >= ctx->hard_eyeballs_timeout_ms) {
|
||||
DEBUGF(LOG_CF(data, cf, "hard timeout of %dms reached, starting h21",
|
||||
ctx->hard_eyeballs_timeout_ms));
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
if(elapsed_ms >= ctx->soft_eyeballs_timeout_ms) {
|
||||
if(cf_hc_baller_reply_ms(&ctx->h3_baller, data) < 0) {
|
||||
DEBUGF(LOG_CF(data, cf, "soft timeout of %dms reached, h3 has not "
|
||||
"seen any data, starting h21",
|
||||
ctx->soft_eyeballs_timeout_ms));
|
||||
return TRUE;
|
||||
}
|
||||
/* set the effective hard timeout again */
|
||||
Curl_expire(data, ctx->hard_eyeballs_timeout_ms - elapsed_ms,
|
||||
EXPIRE_ALPN_EYEBALLS);
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static CURLcode cf_hc_connect(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool blocking, bool *done)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
struct curltime now;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
(void)blocking;
|
||||
if(cf->connected) {
|
||||
*done = TRUE;
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
*done = FALSE;
|
||||
now = Curl_now();
|
||||
switch(ctx->state) {
|
||||
case CF_HC_INIT:
|
||||
DEBUGASSERT(!ctx->h3_baller.cf);
|
||||
DEBUGASSERT(!ctx->h21_baller.cf);
|
||||
DEBUGASSERT(!cf->next);
|
||||
DEBUGF(LOG_CF(data, cf, "connect, init"));
|
||||
ctx->started = now;
|
||||
if(ctx->h3_baller.enabled) {
|
||||
cf_hc_baller_init(&ctx->h3_baller, cf, data, "h3", TRNSPRT_QUIC);
|
||||
if(ctx->h21_baller.enabled)
|
||||
Curl_expire(data, ctx->soft_eyeballs_timeout_ms, EXPIRE_ALPN_EYEBALLS);
|
||||
}
|
||||
else if(ctx->h21_baller.enabled)
|
||||
cf_hc_baller_init(&ctx->h21_baller, cf, data, "h21",
|
||||
cf->conn->transport);
|
||||
ctx->state = CF_HC_CONNECT;
|
||||
/* FALLTHROUGH */
|
||||
|
||||
case CF_HC_CONNECT:
|
||||
if(cf_hc_baller_is_active(&ctx->h3_baller)) {
|
||||
result = cf_hc_baller_connect(&ctx->h3_baller, cf, data, done);
|
||||
if(!result && *done) {
|
||||
result = baller_connected(cf, data, &ctx->h3_baller);
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
if(time_to_start_h21(cf, data, now)) {
|
||||
cf_hc_baller_init(&ctx->h21_baller, cf, data, "h21",
|
||||
cf->conn->transport);
|
||||
}
|
||||
|
||||
if(cf_hc_baller_is_active(&ctx->h21_baller)) {
|
||||
DEBUGF(LOG_CF(data, cf, "connect, check h21"));
|
||||
result = cf_hc_baller_connect(&ctx->h21_baller, cf, data, done);
|
||||
if(!result && *done) {
|
||||
result = baller_connected(cf, data, &ctx->h21_baller);
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
if((!ctx->h3_baller.enabled || ctx->h3_baller.result) &&
|
||||
(!ctx->h21_baller.enabled || ctx->h21_baller.result)) {
|
||||
/* both failed or disabled. we give up */
|
||||
DEBUGF(LOG_CF(data, cf, "connect, all failed"));
|
||||
result = ctx->result = ctx->h3_baller.enabled?
|
||||
ctx->h3_baller.result : ctx->h21_baller.result;
|
||||
ctx->state = CF_HC_FAILURE;
|
||||
goto out;
|
||||
}
|
||||
result = CURLE_OK;
|
||||
*done = FALSE;
|
||||
break;
|
||||
|
||||
case CF_HC_FAILURE:
|
||||
result = ctx->result;
|
||||
cf->connected = FALSE;
|
||||
*done = FALSE;
|
||||
break;
|
||||
|
||||
case CF_HC_SUCCESS:
|
||||
result = CURLE_OK;
|
||||
cf->connected = TRUE;
|
||||
*done = TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
out:
|
||||
DEBUGF(LOG_CF(data, cf, "connect -> %d, done=%d", result, *done));
|
||||
return result;
|
||||
}
|
||||
|
||||
static int cf_hc_get_select_socks(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
curl_socket_t *socks)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
size_t i, j, s;
|
||||
int brc, rc = GETSOCK_BLANK;
|
||||
curl_socket_t bsocks[MAX_SOCKSPEREASYHANDLE];
|
||||
struct cf_hc_baller *ballers[2];
|
||||
|
||||
if(cf->connected)
|
||||
return cf->next->cft->get_select_socks(cf->next, data, socks);
|
||||
|
||||
ballers[0] = &ctx->h3_baller;
|
||||
ballers[1] = &ctx->h21_baller;
|
||||
for(i = s = 0; i < sizeof(ballers)/sizeof(ballers[0]); i++) {
|
||||
struct cf_hc_baller *b = ballers[i];
|
||||
if(!cf_hc_baller_is_active(b))
|
||||
continue;
|
||||
brc = Curl_conn_cf_get_select_socks(b->cf, data, bsocks);
|
||||
DEBUGF(LOG_CF(data, cf, "get_selected_socks(%s) -> %x", b->name, brc));
|
||||
if(!brc)
|
||||
continue;
|
||||
for(j = 0; j < MAX_SOCKSPEREASYHANDLE && s < MAX_SOCKSPEREASYHANDLE; ++j) {
|
||||
if((brc & GETSOCK_WRITESOCK(j)) || (brc & GETSOCK_READSOCK(j))) {
|
||||
socks[s] = bsocks[j];
|
||||
if(brc & GETSOCK_WRITESOCK(j))
|
||||
rc |= GETSOCK_WRITESOCK(s);
|
||||
if(brc & GETSOCK_READSOCK(j))
|
||||
rc |= GETSOCK_READSOCK(s);
|
||||
s++;
|
||||
}
|
||||
}
|
||||
}
|
||||
DEBUGF(LOG_CF(data, cf, "get_selected_socks -> %x", rc));
|
||||
return rc;
|
||||
}
|
||||
|
||||
static bool cf_hc_data_pending(struct Curl_cfilter *cf,
|
||||
const struct Curl_easy *data)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
|
||||
if(cf->connected)
|
||||
return cf->next->cft->has_data_pending(cf->next, data);
|
||||
|
||||
DEBUGF(LOG_CF((struct Curl_easy *)data, cf, "data_pending"));
|
||||
return cf_hc_baller_data_pending(&ctx->h3_baller, data)
|
||||
|| cf_hc_baller_data_pending(&ctx->h21_baller, data);
|
||||
}
|
||||
|
||||
static struct curltime get_max_baller_time(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
int query)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
struct Curl_cfilter *cfb;
|
||||
struct curltime t, tmax;
|
||||
|
||||
memset(&tmax, 0, sizeof(tmax));
|
||||
memset(&t, 0, sizeof(t));
|
||||
cfb = ctx->h21_baller.enabled? ctx->h21_baller.cf : NULL;
|
||||
if(cfb && !cfb->cft->query(cfb, data, query, NULL, &t)) {
|
||||
if((t.tv_sec || t.tv_usec) && Curl_timediff_us(t, tmax) > 0)
|
||||
tmax = t;
|
||||
}
|
||||
memset(&t, 0, sizeof(t));
|
||||
cfb = ctx->h3_baller.enabled? ctx->h3_baller.cf : NULL;
|
||||
if(cfb && !cfb->cft->query(cfb, data, query, NULL, &t)) {
|
||||
if((t.tv_sec || t.tv_usec) && Curl_timediff_us(t, tmax) > 0)
|
||||
tmax = t;
|
||||
}
|
||||
return tmax;
|
||||
}
|
||||
|
||||
static CURLcode cf_hc_query(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
int query, int *pres1, void *pres2)
|
||||
{
|
||||
if(!cf->connected) {
|
||||
switch(query) {
|
||||
case CF_QUERY_TIMER_CONNECT: {
|
||||
struct curltime *when = pres2;
|
||||
*when = get_max_baller_time(cf, data, CF_QUERY_TIMER_CONNECT);
|
||||
return CURLE_OK;
|
||||
}
|
||||
case CF_QUERY_TIMER_APPCONNECT: {
|
||||
struct curltime *when = pres2;
|
||||
*when = get_max_baller_time(cf, data, CF_QUERY_TIMER_APPCONNECT);
|
||||
return CURLE_OK;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
return cf->next?
|
||||
cf->next->cft->query(cf->next, data, query, pres1, pres2) :
|
||||
CURLE_UNKNOWN_OPTION;
|
||||
}
|
||||
|
||||
static void cf_hc_close(struct Curl_cfilter *cf, struct Curl_easy *data)
|
||||
{
|
||||
DEBUGF(LOG_CF(data, cf, "close"));
|
||||
cf_hc_reset(cf, data);
|
||||
cf->connected = FALSE;
|
||||
|
||||
if(cf->next) {
|
||||
cf->next->cft->close(cf->next, data);
|
||||
Curl_conn_cf_discard_chain(&cf->next, data);
|
||||
}
|
||||
}
|
||||
|
||||
static void cf_hc_destroy(struct Curl_cfilter *cf, struct Curl_easy *data)
|
||||
{
|
||||
struct cf_hc_ctx *ctx = cf->ctx;
|
||||
|
||||
(void)data;
|
||||
DEBUGF(LOG_CF(data, cf, "destroy"));
|
||||
cf_hc_reset(cf, data);
|
||||
Curl_safefree(ctx);
|
||||
}
|
||||
|
||||
struct Curl_cftype Curl_cft_http_connect = {
|
||||
"HTTPS-CONNECT",
|
||||
0,
|
||||
CURL_LOG_DEFAULT,
|
||||
cf_hc_destroy,
|
||||
cf_hc_connect,
|
||||
cf_hc_close,
|
||||
Curl_cf_def_get_host,
|
||||
cf_hc_get_select_socks,
|
||||
cf_hc_data_pending,
|
||||
Curl_cf_def_send,
|
||||
Curl_cf_def_recv,
|
||||
Curl_cf_def_cntrl,
|
||||
Curl_cf_def_conn_is_alive,
|
||||
Curl_cf_def_conn_keep_alive,
|
||||
cf_hc_query,
|
||||
};
|
||||
|
||||
static CURLcode cf_hc_create(struct Curl_cfilter **pcf,
|
||||
struct Curl_easy *data,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
bool try_h3, bool try_h21)
|
||||
{
|
||||
struct Curl_cfilter *cf = NULL;
|
||||
struct cf_hc_ctx *ctx;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
(void)data;
|
||||
ctx = calloc(sizeof(*ctx), 1);
|
||||
if(!ctx) {
|
||||
result = CURLE_OUT_OF_MEMORY;
|
||||
goto out;
|
||||
}
|
||||
ctx->remotehost = remotehost;
|
||||
ctx->h3_baller.enabled = try_h3;
|
||||
ctx->h21_baller.enabled = try_h21;
|
||||
|
||||
result = Curl_cf_create(&cf, &Curl_cft_http_connect, ctx);
|
||||
if(result)
|
||||
goto out;
|
||||
ctx = NULL;
|
||||
cf_hc_reset(cf, data);
|
||||
|
||||
out:
|
||||
*pcf = result? NULL : cf;
|
||||
free(ctx);
|
||||
return result;
|
||||
}
|
||||
|
||||
CURLcode Curl_cf_http_connect_add(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
bool try_h3, bool try_h21)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
DEBUGASSERT(data);
|
||||
result = cf_hc_create(&cf, data, remotehost, try_h3, try_h21);
|
||||
if(result)
|
||||
goto out;
|
||||
Curl_conn_cf_add(data, conn, sockindex, cf);
|
||||
out:
|
||||
return result;
|
||||
}
|
||||
|
||||
CURLcode
|
||||
Curl_cf_http_connect_insert_after(struct Curl_cfilter *cf_at,
|
||||
struct Curl_easy *data,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
bool try_h3, bool try_h21)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
CURLcode result;
|
||||
|
||||
DEBUGASSERT(data);
|
||||
result = cf_hc_create(&cf, data, remotehost, try_h3, try_h21);
|
||||
if(result)
|
||||
goto out;
|
||||
Curl_conn_cf_insert_after(cf_at, cf);
|
||||
out:
|
||||
return result;
|
||||
}
|
||||
|
||||
CURLcode Curl_cf_https_setup(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
const struct Curl_dns_entry *remotehost)
|
||||
{
|
||||
bool try_h3 = FALSE, try_h21 = TRUE; /* defaults, for now */
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
(void)sockindex;
|
||||
(void)remotehost;
|
||||
|
||||
if(!conn->bits.tls_enable_alpn)
|
||||
goto out;
|
||||
|
||||
if(data->state.httpwant == CURL_HTTP_VERSION_3ONLY) {
|
||||
result = Curl_conn_may_http3(data, conn);
|
||||
if(result) /* can't do it */
|
||||
goto out;
|
||||
try_h3 = TRUE;
|
||||
try_h21 = FALSE;
|
||||
}
|
||||
else if(data->state.httpwant >= CURL_HTTP_VERSION_3) {
|
||||
/* We assume that silently not even trying H3 is ok here */
|
||||
/* TODO: should we fail instead? */
|
||||
try_h3 = (Curl_conn_may_http3(data, conn) == CURLE_OK);
|
||||
try_h21 = TRUE;
|
||||
}
|
||||
|
||||
result = Curl_cf_http_connect_add(data, conn, sockindex, remotehost,
|
||||
try_h3, try_h21);
|
||||
out:
|
||||
return result;
|
||||
}
|
||||
|
||||
#endif /* !defined(CURL_DISABLE_HTTP) && !defined(USE_HYPER) */
|
58
src/dependencies/cmcurl/lib/cf-https-connect.h
Normal file
58
src/dependencies/cmcurl/lib/cf-https-connect.h
Normal file
|
@ -0,0 +1,58 @@
|
|||
#ifndef HEADER_CURL_CF_HTTP_H
|
||||
#define HEADER_CURL_CF_HTTP_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if !defined(CURL_DISABLE_HTTP) && !defined(USE_HYPER)
|
||||
|
||||
struct Curl_cfilter;
|
||||
struct Curl_easy;
|
||||
struct connectdata;
|
||||
struct Curl_cftype;
|
||||
struct Curl_dns_entry;
|
||||
|
||||
extern struct Curl_cftype Curl_cft_http_connect;
|
||||
|
||||
CURLcode Curl_cf_http_connect_add(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
bool try_h3, bool try_h21);
|
||||
|
||||
CURLcode
|
||||
Curl_cf_http_connect_insert_after(struct Curl_cfilter *cf_at,
|
||||
struct Curl_easy *data,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
bool try_h3, bool try_h21);
|
||||
|
||||
|
||||
CURLcode Curl_cf_https_setup(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
const struct Curl_dns_entry *remotehost);
|
||||
|
||||
|
||||
#endif /* !defined(CURL_DISABLE_HTTP) && !defined(USE_HYPER) */
|
||||
#endif /* HEADER_CURL_CF_HTTP_H */
|
1921
src/dependencies/cmcurl/lib/cf-socket.c
Normal file
1921
src/dependencies/cmcurl/lib/cf-socket.c
Normal file
File diff suppressed because it is too large
Load diff
185
src/dependencies/cmcurl/lib/cf-socket.h
Normal file
185
src/dependencies/cmcurl/lib/cf-socket.h
Normal file
|
@ -0,0 +1,185 @@
|
|||
#ifndef HEADER_CURL_CF_SOCKET_H
|
||||
#define HEADER_CURL_CF_SOCKET_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
#include "nonblock.h" /* for curlx_nonblock(), formerly Curl_nonblock() */
|
||||
#include "sockaddr.h"
|
||||
|
||||
struct Curl_addrinfo;
|
||||
struct Curl_cfilter;
|
||||
struct Curl_easy;
|
||||
struct connectdata;
|
||||
struct Curl_sockaddr_ex;
|
||||
|
||||
/*
|
||||
* The Curl_sockaddr_ex structure is basically libcurl's external API
|
||||
* curl_sockaddr structure with enough space available to directly hold any
|
||||
* protocol-specific address structures. The variable declared here will be
|
||||
* used to pass / receive data to/from the fopensocket callback if this has
|
||||
* been set, before that, it is initialized from parameters.
|
||||
*/
|
||||
struct Curl_sockaddr_ex {
|
||||
int family;
|
||||
int socktype;
|
||||
int protocol;
|
||||
unsigned int addrlen;
|
||||
union {
|
||||
struct sockaddr addr;
|
||||
struct Curl_sockaddr_storage buff;
|
||||
} _sa_ex_u;
|
||||
};
|
||||
#define sa_addr _sa_ex_u.addr
|
||||
|
||||
|
||||
/*
|
||||
* Create a socket based on info from 'conn' and 'ai'.
|
||||
*
|
||||
* Fill in 'addr' and 'sockfd' accordingly if OK is returned. If the open
|
||||
* socket callback is set, used that!
|
||||
*
|
||||
*/
|
||||
CURLcode Curl_socket_open(struct Curl_easy *data,
|
||||
const struct Curl_addrinfo *ai,
|
||||
struct Curl_sockaddr_ex *addr,
|
||||
int transport,
|
||||
curl_socket_t *sockfd);
|
||||
|
||||
int Curl_socket_close(struct Curl_easy *data, struct connectdata *conn,
|
||||
curl_socket_t sock);
|
||||
|
||||
/**
|
||||
* Determine the curl code for a socket connect() == -1 with errno.
|
||||
*/
|
||||
CURLcode Curl_socket_connect_result(struct Curl_easy *data,
|
||||
const char *ipaddress, int error);
|
||||
|
||||
#ifdef USE_WINSOCK
|
||||
/* When you run a program that uses the Windows Sockets API, you may
|
||||
experience slow performance when you copy data to a TCP server.
|
||||
|
||||
https://support.microsoft.com/kb/823764
|
||||
|
||||
Work-around: Make the Socket Send Buffer Size Larger Than the Program Send
|
||||
Buffer Size
|
||||
|
||||
*/
|
||||
void Curl_sndbufset(curl_socket_t sockfd);
|
||||
#else
|
||||
#define Curl_sndbufset(y) Curl_nop_stmt
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Assign the address `ai` to the Curl_sockaddr_ex `dest` and
|
||||
* set the transport used.
|
||||
*/
|
||||
void Curl_sock_assign_addr(struct Curl_sockaddr_ex *dest,
|
||||
const struct Curl_addrinfo *ai,
|
||||
int transport);
|
||||
|
||||
/**
|
||||
* Creates a cfilter that opens a TCP socket to the given address
|
||||
* when calling its `connect` implementation.
|
||||
* The filter will not touch any connection/data flags and can be
|
||||
* used in happy eyeballing. Once selected for use, its `_active()`
|
||||
* method needs to be called.
|
||||
*/
|
||||
CURLcode Curl_cf_tcp_create(struct Curl_cfilter **pcf,
|
||||
struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
const struct Curl_addrinfo *ai,
|
||||
int transport);
|
||||
|
||||
/**
|
||||
* Creates a cfilter that opens a UDP socket to the given address
|
||||
* when calling its `connect` implementation.
|
||||
* The filter will not touch any connection/data flags and can be
|
||||
* used in happy eyeballing. Once selected for use, its `_active()`
|
||||
* method needs to be called.
|
||||
*/
|
||||
CURLcode Curl_cf_udp_create(struct Curl_cfilter **pcf,
|
||||
struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
const struct Curl_addrinfo *ai,
|
||||
int transport);
|
||||
|
||||
/**
|
||||
* Creates a cfilter that opens a UNIX socket to the given address
|
||||
* when calling its `connect` implementation.
|
||||
* The filter will not touch any connection/data flags and can be
|
||||
* used in happy eyeballing. Once selected for use, its `_active()`
|
||||
* method needs to be called.
|
||||
*/
|
||||
CURLcode Curl_cf_unix_create(struct Curl_cfilter **pcf,
|
||||
struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
const struct Curl_addrinfo *ai,
|
||||
int transport);
|
||||
|
||||
/**
|
||||
* Creates a cfilter that keeps a listening socket.
|
||||
*/
|
||||
CURLcode Curl_conn_tcp_listen_set(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
curl_socket_t *s);
|
||||
|
||||
/**
|
||||
* Replace the listen socket with the accept()ed one.
|
||||
*/
|
||||
CURLcode Curl_conn_tcp_accepted_set(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
curl_socket_t *s);
|
||||
|
||||
/**
|
||||
* Return TRUE iff `cf` is a socket filter.
|
||||
*/
|
||||
bool Curl_cf_is_socket(struct Curl_cfilter *cf);
|
||||
|
||||
/**
|
||||
* Peek at the socket and remote ip/port the socket filter is using.
|
||||
* The filter owns all returned values.
|
||||
* @param psock pointer to hold socket descriptor or NULL
|
||||
* @param paddr pointer to hold addr reference or NULL
|
||||
* @param pr_ip_str pointer to hold remote addr as string or NULL
|
||||
* @param pr_port pointer to hold remote port number or NULL
|
||||
* @param pl_ip_str pointer to hold local addr as string or NULL
|
||||
* @param pl_port pointer to hold local port number or NULL
|
||||
* Returns error if the filter is of invalid type.
|
||||
*/
|
||||
CURLcode Curl_cf_socket_peek(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
curl_socket_t *psock,
|
||||
const struct Curl_sockaddr_ex **paddr,
|
||||
const char **pr_ip_str, int *pr_port,
|
||||
const char **pl_ip_str, int *pl_port);
|
||||
|
||||
extern struct Curl_cftype Curl_cft_tcp;
|
||||
extern struct Curl_cftype Curl_cft_udp;
|
||||
extern struct Curl_cftype Curl_cft_unix;
|
||||
extern struct Curl_cftype Curl_cft_tcp_accept;
|
||||
|
||||
#endif /* HEADER_CURL_CF_SOCKET_H */
|
663
src/dependencies/cmcurl/lib/cfilters.c
Normal file
663
src/dependencies/cmcurl/lib/cfilters.c
Normal file
|
@ -0,0 +1,663 @@
|
|||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#include "urldata.h"
|
||||
#include "strerror.h"
|
||||
#include "cfilters.h"
|
||||
#include "connect.h"
|
||||
#include "url.h" /* for Curl_safefree() */
|
||||
#include "sendf.h"
|
||||
#include "sockaddr.h" /* required for Curl_sockaddr_storage */
|
||||
#include "multiif.h"
|
||||
#include "progress.h"
|
||||
#include "warnless.h"
|
||||
|
||||
/* The last 3 #include files should be in this order */
|
||||
#include "curl_printf.h"
|
||||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
#ifndef ARRAYSIZE
|
||||
#define ARRAYSIZE(A) (sizeof(A)/sizeof((A)[0]))
|
||||
#endif
|
||||
|
||||
|
||||
void Curl_cf_def_destroy_this(struct Curl_cfilter *cf, struct Curl_easy *data)
|
||||
{
|
||||
(void)cf;
|
||||
(void)data;
|
||||
}
|
||||
|
||||
void Curl_cf_def_close(struct Curl_cfilter *cf, struct Curl_easy *data)
|
||||
{
|
||||
cf->connected = FALSE;
|
||||
if(cf->next)
|
||||
cf->next->cft->close(cf->next, data);
|
||||
}
|
||||
|
||||
CURLcode Curl_cf_def_connect(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool blocking, bool *done)
|
||||
{
|
||||
CURLcode result;
|
||||
|
||||
if(cf->connected) {
|
||||
*done = TRUE;
|
||||
return CURLE_OK;
|
||||
}
|
||||
if(cf->next) {
|
||||
result = cf->next->cft->connect(cf->next, data, blocking, done);
|
||||
if(!result && *done) {
|
||||
cf->connected = TRUE;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
*done = FALSE;
|
||||
return CURLE_FAILED_INIT;
|
||||
}
|
||||
|
||||
void Curl_cf_def_get_host(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
const char **phost, const char **pdisplay_host,
|
||||
int *pport)
|
||||
{
|
||||
if(cf->next)
|
||||
cf->next->cft->get_host(cf->next, data, phost, pdisplay_host, pport);
|
||||
else {
|
||||
*phost = cf->conn->host.name;
|
||||
*pdisplay_host = cf->conn->host.dispname;
|
||||
*pport = cf->conn->port;
|
||||
}
|
||||
}
|
||||
|
||||
int Curl_cf_def_get_select_socks(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
curl_socket_t *socks)
|
||||
{
|
||||
return cf->next?
|
||||
cf->next->cft->get_select_socks(cf->next, data, socks) : 0;
|
||||
}
|
||||
|
||||
bool Curl_cf_def_data_pending(struct Curl_cfilter *cf,
|
||||
const struct Curl_easy *data)
|
||||
{
|
||||
return cf->next?
|
||||
cf->next->cft->has_data_pending(cf->next, data) : FALSE;
|
||||
}
|
||||
|
||||
ssize_t Curl_cf_def_send(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
const void *buf, size_t len, CURLcode *err)
|
||||
{
|
||||
return cf->next?
|
||||
cf->next->cft->do_send(cf->next, data, buf, len, err) :
|
||||
CURLE_RECV_ERROR;
|
||||
}
|
||||
|
||||
ssize_t Curl_cf_def_recv(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
char *buf, size_t len, CURLcode *err)
|
||||
{
|
||||
return cf->next?
|
||||
cf->next->cft->do_recv(cf->next, data, buf, len, err) :
|
||||
CURLE_SEND_ERROR;
|
||||
}
|
||||
|
||||
bool Curl_cf_def_conn_is_alive(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool *input_pending)
|
||||
{
|
||||
return cf->next?
|
||||
cf->next->cft->is_alive(cf->next, data, input_pending) :
|
||||
FALSE; /* pessimistic in absence of data */
|
||||
}
|
||||
|
||||
CURLcode Curl_cf_def_conn_keep_alive(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data)
|
||||
{
|
||||
return cf->next?
|
||||
cf->next->cft->keep_alive(cf->next, data) :
|
||||
CURLE_OK;
|
||||
}
|
||||
|
||||
CURLcode Curl_cf_def_query(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
int query, int *pres1, void *pres2)
|
||||
{
|
||||
return cf->next?
|
||||
cf->next->cft->query(cf->next, data, query, pres1, pres2) :
|
||||
CURLE_UNKNOWN_OPTION;
|
||||
}
|
||||
|
||||
void Curl_conn_cf_discard_chain(struct Curl_cfilter **pcf,
|
||||
struct Curl_easy *data)
|
||||
{
|
||||
struct Curl_cfilter *cfn, *cf = *pcf;
|
||||
|
||||
if(cf) {
|
||||
*pcf = NULL;
|
||||
while(cf) {
|
||||
cfn = cf->next;
|
||||
/* prevent destroying filter to mess with its sub-chain, since
|
||||
* we have the reference now and will call destroy on it.
|
||||
*/
|
||||
cf->next = NULL;
|
||||
cf->cft->destroy(cf, data);
|
||||
free(cf);
|
||||
cf = cfn;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Curl_conn_cf_discard_all(struct Curl_easy *data,
|
||||
struct connectdata *conn, int index)
|
||||
{
|
||||
Curl_conn_cf_discard_chain(&conn->cfilter[index], data);
|
||||
}
|
||||
|
||||
void Curl_conn_close(struct Curl_easy *data, int index)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
DEBUGASSERT(data->conn);
|
||||
/* it is valid to call that without filters being present */
|
||||
cf = data->conn->cfilter[index];
|
||||
if(cf) {
|
||||
cf->cft->close(cf, data);
|
||||
}
|
||||
}
|
||||
|
||||
ssize_t Curl_conn_recv(struct Curl_easy *data, int num, char *buf,
|
||||
size_t len, CURLcode *code)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
DEBUGASSERT(data);
|
||||
DEBUGASSERT(data->conn);
|
||||
cf = data->conn->cfilter[num];
|
||||
while(cf && !cf->connected) {
|
||||
cf = cf->next;
|
||||
}
|
||||
if(cf) {
|
||||
return cf->cft->do_recv(cf, data, buf, len, code);
|
||||
}
|
||||
failf(data, CMSGI(data->conn, num, "recv: no filter connected"));
|
||||
*code = CURLE_FAILED_INIT;
|
||||
return -1;
|
||||
}
|
||||
|
||||
ssize_t Curl_conn_send(struct Curl_easy *data, int num,
|
||||
const void *mem, size_t len, CURLcode *code)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
DEBUGASSERT(data);
|
||||
DEBUGASSERT(data->conn);
|
||||
cf = data->conn->cfilter[num];
|
||||
while(cf && !cf->connected) {
|
||||
cf = cf->next;
|
||||
}
|
||||
if(cf) {
|
||||
return cf->cft->do_send(cf, data, mem, len, code);
|
||||
}
|
||||
failf(data, CMSGI(data->conn, num, "send: no filter connected"));
|
||||
DEBUGASSERT(0);
|
||||
*code = CURLE_FAILED_INIT;
|
||||
return -1;
|
||||
}
|
||||
|
||||
CURLcode Curl_cf_create(struct Curl_cfilter **pcf,
|
||||
const struct Curl_cftype *cft,
|
||||
void *ctx)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
CURLcode result = CURLE_OUT_OF_MEMORY;
|
||||
|
||||
DEBUGASSERT(cft);
|
||||
cf = calloc(sizeof(*cf), 1);
|
||||
if(!cf)
|
||||
goto out;
|
||||
|
||||
cf->cft = cft;
|
||||
cf->ctx = ctx;
|
||||
result = CURLE_OK;
|
||||
out:
|
||||
*pcf = cf;
|
||||
return result;
|
||||
}
|
||||
|
||||
void Curl_conn_cf_add(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int index,
|
||||
struct Curl_cfilter *cf)
|
||||
{
|
||||
(void)data;
|
||||
DEBUGASSERT(conn);
|
||||
DEBUGASSERT(!cf->conn);
|
||||
DEBUGASSERT(!cf->next);
|
||||
|
||||
cf->next = conn->cfilter[index];
|
||||
cf->conn = conn;
|
||||
cf->sockindex = index;
|
||||
conn->cfilter[index] = cf;
|
||||
DEBUGF(LOG_CF(data, cf, "added"));
|
||||
}
|
||||
|
||||
void Curl_conn_cf_insert_after(struct Curl_cfilter *cf_at,
|
||||
struct Curl_cfilter *cf_new)
|
||||
{
|
||||
struct Curl_cfilter *tail, **pnext;
|
||||
|
||||
DEBUGASSERT(cf_at);
|
||||
DEBUGASSERT(cf_new);
|
||||
DEBUGASSERT(!cf_new->conn);
|
||||
|
||||
tail = cf_at->next;
|
||||
cf_at->next = cf_new;
|
||||
do {
|
||||
cf_new->conn = cf_at->conn;
|
||||
cf_new->sockindex = cf_at->sockindex;
|
||||
pnext = &cf_new->next;
|
||||
cf_new = cf_new->next;
|
||||
} while(cf_new);
|
||||
*pnext = tail;
|
||||
}
|
||||
|
||||
void Curl_conn_cf_discard(struct Curl_cfilter *cf, struct Curl_easy *data)
|
||||
{
|
||||
struct Curl_cfilter **pprev = &cf->conn->cfilter[cf->sockindex];
|
||||
|
||||
/* remove from chain if still in there */
|
||||
DEBUGASSERT(cf);
|
||||
while (*pprev) {
|
||||
if (*pprev == cf) {
|
||||
*pprev = cf->next;
|
||||
break;
|
||||
}
|
||||
pprev = &((*pprev)->next);
|
||||
}
|
||||
cf->cft->destroy(cf, data);
|
||||
free(cf);
|
||||
}
|
||||
|
||||
CURLcode Curl_conn_cf_connect(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool blocking, bool *done)
|
||||
{
|
||||
if(cf)
|
||||
return cf->cft->connect(cf, data, blocking, done);
|
||||
return CURLE_FAILED_INIT;
|
||||
}
|
||||
|
||||
void Curl_conn_cf_close(struct Curl_cfilter *cf, struct Curl_easy *data)
|
||||
{
|
||||
if(cf)
|
||||
cf->cft->close(cf, data);
|
||||
}
|
||||
|
||||
int Curl_conn_cf_get_select_socks(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
curl_socket_t *socks)
|
||||
{
|
||||
if(cf)
|
||||
return cf->cft->get_select_socks(cf, data, socks);
|
||||
return 0;
|
||||
}
|
||||
|
||||
bool Curl_conn_cf_data_pending(struct Curl_cfilter *cf,
|
||||
const struct Curl_easy *data)
|
||||
{
|
||||
if(cf)
|
||||
return cf->cft->has_data_pending(cf, data);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
ssize_t Curl_conn_cf_send(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
const void *buf, size_t len, CURLcode *err)
|
||||
{
|
||||
if(cf)
|
||||
return cf->cft->do_send(cf, data, buf, len, err);
|
||||
*err = CURLE_SEND_ERROR;
|
||||
return -1;
|
||||
}
|
||||
|
||||
ssize_t Curl_conn_cf_recv(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
char *buf, size_t len, CURLcode *err)
|
||||
{
|
||||
if(cf)
|
||||
return cf->cft->do_recv(cf, data, buf, len, err);
|
||||
*err = CURLE_RECV_ERROR;
|
||||
return -1;
|
||||
}
|
||||
|
||||
CURLcode Curl_conn_connect(struct Curl_easy *data,
|
||||
int sockindex,
|
||||
bool blocking,
|
||||
bool *done)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
DEBUGASSERT(data);
|
||||
DEBUGASSERT(data->conn);
|
||||
|
||||
cf = data->conn->cfilter[sockindex];
|
||||
DEBUGASSERT(cf);
|
||||
if(!cf)
|
||||
return CURLE_FAILED_INIT;
|
||||
|
||||
*done = cf->connected;
|
||||
if(!*done) {
|
||||
result = cf->cft->connect(cf, data, blocking, done);
|
||||
if(!result && *done) {
|
||||
Curl_conn_ev_update_info(data, data->conn);
|
||||
Curl_conn_report_connect_stats(data, data->conn);
|
||||
data->conn->keepalive = Curl_now();
|
||||
}
|
||||
else if(result) {
|
||||
Curl_conn_report_connect_stats(data, data->conn);
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
bool Curl_conn_is_connected(struct connectdata *conn, int sockindex)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
cf = conn->cfilter[sockindex];
|
||||
return cf && cf->connected;
|
||||
}
|
||||
|
||||
bool Curl_conn_is_ip_connected(struct Curl_easy *data, int sockindex)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
cf = data->conn->cfilter[sockindex];
|
||||
while(cf) {
|
||||
if(cf->connected)
|
||||
return TRUE;
|
||||
if(cf->cft->flags & CF_TYPE_IP_CONNECT)
|
||||
return FALSE;
|
||||
cf = cf->next;
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
bool Curl_conn_is_ssl(struct connectdata *conn, int sockindex)
|
||||
{
|
||||
struct Curl_cfilter *cf = conn? conn->cfilter[sockindex] : NULL;
|
||||
|
||||
for(; cf; cf = cf->next) {
|
||||
if(cf->cft->flags & CF_TYPE_SSL)
|
||||
return TRUE;
|
||||
if(cf->cft->flags & CF_TYPE_IP_CONNECT)
|
||||
return FALSE;
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
bool Curl_conn_is_multiplex(struct connectdata *conn, int sockindex)
|
||||
{
|
||||
struct Curl_cfilter *cf = conn? conn->cfilter[sockindex] : NULL;
|
||||
|
||||
for(; cf; cf = cf->next) {
|
||||
if(cf->cft->flags & CF_TYPE_MULTIPLEX)
|
||||
return TRUE;
|
||||
if(cf->cft->flags & CF_TYPE_IP_CONNECT
|
||||
|| cf->cft->flags & CF_TYPE_SSL)
|
||||
return FALSE;
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
bool Curl_conn_data_pending(struct Curl_easy *data, int sockindex)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
(void)data;
|
||||
DEBUGASSERT(data);
|
||||
DEBUGASSERT(data->conn);
|
||||
|
||||
cf = data->conn->cfilter[sockindex];
|
||||
while(cf && !cf->connected) {
|
||||
cf = cf->next;
|
||||
}
|
||||
if(cf) {
|
||||
return cf->cft->has_data_pending(cf, data);
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
int Curl_conn_get_select_socks(struct Curl_easy *data, int sockindex,
|
||||
curl_socket_t *socks)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
DEBUGASSERT(data);
|
||||
DEBUGASSERT(data->conn);
|
||||
cf = data->conn->cfilter[sockindex];
|
||||
|
||||
/* if the next one is not yet connected, that's the one we want */
|
||||
while(cf && cf->next && !cf->next->connected)
|
||||
cf = cf->next;
|
||||
if(cf) {
|
||||
return cf->cft->get_select_socks(cf, data, socks);
|
||||
}
|
||||
return GETSOCK_BLANK;
|
||||
}
|
||||
|
||||
void Curl_conn_get_host(struct Curl_easy *data, int sockindex,
|
||||
const char **phost, const char **pdisplay_host,
|
||||
int *pport)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
DEBUGASSERT(data->conn);
|
||||
cf = data->conn->cfilter[sockindex];
|
||||
if(cf) {
|
||||
cf->cft->get_host(cf, data, phost, pdisplay_host, pport);
|
||||
}
|
||||
else {
|
||||
/* Some filter ask during shutdown for this, mainly for debugging
|
||||
* purposes. We hand out the defaults, however this is not always
|
||||
* accurate, as the connection might be tunneled, etc. But all that
|
||||
* state is already gone here. */
|
||||
*phost = data->conn->host.name;
|
||||
*pdisplay_host = data->conn->host.dispname;
|
||||
*pport = data->conn->remote_port;
|
||||
}
|
||||
}
|
||||
|
||||
CURLcode Curl_cf_def_cntrl(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
int event, int arg1, void *arg2)
|
||||
{
|
||||
(void)cf;
|
||||
(void)data;
|
||||
(void)event;
|
||||
(void)arg1;
|
||||
(void)arg2;
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
CURLcode Curl_conn_cf_cntrl(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool ignore_result,
|
||||
int event, int arg1, void *arg2)
|
||||
{
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
for(; cf; cf = cf->next) {
|
||||
if(Curl_cf_def_cntrl == cf->cft->cntrl)
|
||||
continue;
|
||||
result = cf->cft->cntrl(cf, data, event, arg1, arg2);
|
||||
if(!ignore_result && result)
|
||||
break;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
curl_socket_t Curl_conn_cf_get_socket(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data)
|
||||
{
|
||||
curl_socket_t sock;
|
||||
if(cf && !cf->cft->query(cf, data, CF_QUERY_SOCKET, NULL, &sock))
|
||||
return sock;
|
||||
return CURL_SOCKET_BAD;
|
||||
}
|
||||
|
||||
curl_socket_t Curl_conn_get_socket(struct Curl_easy *data, int sockindex)
|
||||
{
|
||||
struct Curl_cfilter *cf;
|
||||
|
||||
cf = data->conn? data->conn->cfilter[sockindex] : NULL;
|
||||
/* if the top filter has not connected, ask it (and its sub-filters)
|
||||
* for the socket. Otherwise conn->sock[sockindex] should have it.
|
||||
*/
|
||||
if(cf && !cf->connected)
|
||||
return Curl_conn_cf_get_socket(cf, data);
|
||||
return data->conn? data->conn->sock[sockindex] : CURL_SOCKET_BAD;
|
||||
}
|
||||
|
||||
static CURLcode cf_cntrl_all(struct connectdata *conn,
|
||||
struct Curl_easy *data,
|
||||
bool ignore_result,
|
||||
int event, int arg1, void *arg2)
|
||||
{
|
||||
CURLcode result = CURLE_OK;
|
||||
size_t i;
|
||||
|
||||
for(i = 0; i < ARRAYSIZE(conn->cfilter); ++i) {
|
||||
result = Curl_conn_cf_cntrl(conn->cfilter[i], data, ignore_result,
|
||||
event, arg1, arg2);
|
||||
if(!ignore_result && result)
|
||||
break;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
void Curl_conn_ev_data_attach(struct connectdata *conn,
|
||||
struct Curl_easy *data)
|
||||
{
|
||||
cf_cntrl_all(conn, data, TRUE, CF_CTRL_DATA_ATTACH, 0, NULL);
|
||||
}
|
||||
|
||||
void Curl_conn_ev_data_detach(struct connectdata *conn,
|
||||
struct Curl_easy *data)
|
||||
{
|
||||
cf_cntrl_all(conn, data, TRUE, CF_CTRL_DATA_DETACH, 0, NULL);
|
||||
}
|
||||
|
||||
CURLcode Curl_conn_ev_data_setup(struct Curl_easy *data)
|
||||
{
|
||||
return cf_cntrl_all(data->conn, data, FALSE,
|
||||
CF_CTRL_DATA_SETUP, 0, NULL);
|
||||
}
|
||||
|
||||
CURLcode Curl_conn_ev_data_idle(struct Curl_easy *data)
|
||||
{
|
||||
return cf_cntrl_all(data->conn, data, FALSE,
|
||||
CF_CTRL_DATA_IDLE, 0, NULL);
|
||||
}
|
||||
|
||||
/**
|
||||
* Notify connection filters that the transfer represented by `data`
|
||||
* is donw with sending data (e.g. has uploaded everything).
|
||||
*/
|
||||
void Curl_conn_ev_data_done_send(struct Curl_easy *data)
|
||||
{
|
||||
cf_cntrl_all(data->conn, data, TRUE, CF_CTRL_DATA_DONE_SEND, 0, NULL);
|
||||
}
|
||||
|
||||
/**
|
||||
* Notify connection filters that the transfer represented by `data`
|
||||
* is finished - eventually premature, e.g. before being complete.
|
||||
*/
|
||||
void Curl_conn_ev_data_done(struct Curl_easy *data, bool premature)
|
||||
{
|
||||
cf_cntrl_all(data->conn, data, TRUE, CF_CTRL_DATA_DONE, premature, NULL);
|
||||
}
|
||||
|
||||
CURLcode Curl_conn_ev_data_pause(struct Curl_easy *data, bool do_pause)
|
||||
{
|
||||
return cf_cntrl_all(data->conn, data, FALSE,
|
||||
CF_CTRL_DATA_PAUSE, do_pause, NULL);
|
||||
}
|
||||
|
||||
void Curl_conn_ev_update_info(struct Curl_easy *data,
|
||||
struct connectdata *conn)
|
||||
{
|
||||
cf_cntrl_all(conn, data, TRUE, CF_CTRL_CONN_INFO_UPDATE, 0, NULL);
|
||||
}
|
||||
|
||||
void Curl_conn_report_connect_stats(struct Curl_easy *data,
|
||||
struct connectdata *conn)
|
||||
{
|
||||
struct Curl_cfilter *cf = conn->cfilter[FIRSTSOCKET];
|
||||
if(cf) {
|
||||
struct curltime connected;
|
||||
struct curltime appconnected;
|
||||
|
||||
memset(&connected, 0, sizeof(connected));
|
||||
cf->cft->query(cf, data, CF_QUERY_TIMER_CONNECT, NULL, &connected);
|
||||
if(connected.tv_sec || connected.tv_usec)
|
||||
Curl_pgrsTimeWas(data, TIMER_CONNECT, connected);
|
||||
|
||||
memset(&appconnected, 0, sizeof(appconnected));
|
||||
cf->cft->query(cf, data, CF_QUERY_TIMER_APPCONNECT, NULL, &appconnected);
|
||||
if(appconnected.tv_sec || appconnected.tv_usec)
|
||||
Curl_pgrsTimeWas(data, TIMER_APPCONNECT, appconnected);
|
||||
}
|
||||
}
|
||||
|
||||
bool Curl_conn_is_alive(struct Curl_easy *data, struct connectdata *conn,
|
||||
bool *input_pending)
|
||||
{
|
||||
struct Curl_cfilter *cf = conn->cfilter[FIRSTSOCKET];
|
||||
return cf && !cf->conn->bits.close &&
|
||||
cf->cft->is_alive(cf, data, input_pending);
|
||||
}
|
||||
|
||||
CURLcode Curl_conn_keep_alive(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex)
|
||||
{
|
||||
struct Curl_cfilter *cf = conn->cfilter[sockindex];
|
||||
return cf? cf->cft->keep_alive(cf, data) : CURLE_OK;
|
||||
}
|
||||
|
||||
size_t Curl_conn_get_max_concurrent(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex)
|
||||
{
|
||||
CURLcode result;
|
||||
int n = 0;
|
||||
|
||||
struct Curl_cfilter *cf = conn->cfilter[sockindex];
|
||||
result = cf? cf->cft->query(cf, data, CF_QUERY_MAX_CONCURRENT,
|
||||
&n, NULL) : CURLE_UNKNOWN_OPTION;
|
||||
return (result || n <= 0)? 1 : (size_t)n;
|
||||
}
|
||||
|
539
src/dependencies/cmcurl/lib/cfilters.h
Normal file
539
src/dependencies/cmcurl/lib/cfilters.h
Normal file
|
@ -0,0 +1,539 @@
|
|||
#ifndef HEADER_CURL_CFILTERS_H
|
||||
#define HEADER_CURL_CFILTERS_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
|
||||
struct Curl_cfilter;
|
||||
struct Curl_easy;
|
||||
struct Curl_dns_entry;
|
||||
struct connectdata;
|
||||
|
||||
/* Callback to destroy resources held by this filter instance.
|
||||
* Implementations MUST NOT chain calls to cf->next.
|
||||
*/
|
||||
typedef void Curl_cft_destroy_this(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data);
|
||||
|
||||
typedef void Curl_cft_close(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data);
|
||||
|
||||
typedef CURLcode Curl_cft_connect(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool blocking, bool *done);
|
||||
|
||||
/* Return the hostname and port the connection goes to.
|
||||
* This may change with the connection state of filters when tunneling
|
||||
* is involved.
|
||||
* @param cf the filter to ask
|
||||
* @param data the easy handle currently active
|
||||
* @param phost on return, points to the relevant, real hostname.
|
||||
* this is owned by the connection.
|
||||
* @param pdisplay_host on return, points to the printable hostname.
|
||||
* this is owned by the connection.
|
||||
* @param pport on return, contains the port number
|
||||
*/
|
||||
typedef void Curl_cft_get_host(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
const char **phost,
|
||||
const char **pdisplay_host,
|
||||
int *pport);
|
||||
|
||||
/* Filters may return sockets and fdset flags they are waiting for.
|
||||
* The passes array has room for up to MAX_SOCKSPEREASYHANDLE sockets.
|
||||
* @return read/write fdset for index in socks
|
||||
* or GETSOCK_BLANK when nothing to wait on
|
||||
*/
|
||||
typedef int Curl_cft_get_select_socks(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
curl_socket_t *socks);
|
||||
|
||||
typedef bool Curl_cft_data_pending(struct Curl_cfilter *cf,
|
||||
const struct Curl_easy *data);
|
||||
|
||||
typedef ssize_t Curl_cft_send(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data, /* transfer */
|
||||
const void *buf, /* data to write */
|
||||
size_t len, /* amount to write */
|
||||
CURLcode *err); /* error to return */
|
||||
|
||||
typedef ssize_t Curl_cft_recv(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data, /* transfer */
|
||||
char *buf, /* store data here */
|
||||
size_t len, /* amount to read */
|
||||
CURLcode *err); /* error to return */
|
||||
|
||||
typedef bool Curl_cft_conn_is_alive(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool *input_pending);
|
||||
|
||||
typedef CURLcode Curl_cft_conn_keep_alive(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data);
|
||||
|
||||
/**
|
||||
* Events/controls for connection filters, their arguments and
|
||||
* return code handling. Filter callbacks are invoked "top down".
|
||||
* Return code handling:
|
||||
* "first fail" meaning that the first filter returning != CURLE_OK, will
|
||||
* abort further event distribution and determine the result.
|
||||
* "ignored" meaning return values are ignored and the event is distributed
|
||||
* to all filters in the chain. Overall result is always CURLE_OK.
|
||||
*/
|
||||
/* data event arg1 arg2 return */
|
||||
#define CF_CTRL_DATA_ATTACH 1 /* 0 NULL ignored */
|
||||
#define CF_CTRL_DATA_DETACH 2 /* 0 NULL ignored */
|
||||
#define CF_CTRL_DATA_SETUP 4 /* 0 NULL first fail */
|
||||
#define CF_CTRL_DATA_IDLE 5 /* 0 NULL first fail */
|
||||
#define CF_CTRL_DATA_PAUSE 6 /* on/off NULL first fail */
|
||||
#define CF_CTRL_DATA_DONE 7 /* premature NULL ignored */
|
||||
#define CF_CTRL_DATA_DONE_SEND 8 /* 0 NULL ignored */
|
||||
/* update conn info at connection and data */
|
||||
#define CF_CTRL_CONN_INFO_UPDATE (256+0) /* 0 NULL ignored */
|
||||
|
||||
/**
|
||||
* Handle event/control for the filter.
|
||||
* Implementations MUST NOT chain calls to cf->next.
|
||||
*/
|
||||
typedef CURLcode Curl_cft_cntrl(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
int event, int arg1, void *arg2);
|
||||
|
||||
|
||||
/**
|
||||
* Queries to ask via a `Curl_cft_query *query` method on a cfilter chain.
|
||||
* - MAX_CONCURRENT: the maximum number of parallel transfers the filter
|
||||
* chain expects to handle at the same time.
|
||||
* default: 1 if no filter overrides.
|
||||
* - CONNECT_REPLY_MS: milliseconds until the first indication of a server
|
||||
* response was received on a connect. For TCP, this
|
||||
* reflects the time until the socket connected. On UDP
|
||||
* this gives the time the first bytes from the server
|
||||
* were received.
|
||||
* -1 if not determined yet.
|
||||
* - CF_QUERY_SOCKET: the socket used by the filter chain
|
||||
*/
|
||||
/* query res1 res2 */
|
||||
#define CF_QUERY_MAX_CONCURRENT 1 /* number - */
|
||||
#define CF_QUERY_CONNECT_REPLY_MS 2 /* number - */
|
||||
#define CF_QUERY_SOCKET 3 /* - curl_socket_t */
|
||||
#define CF_QUERY_TIMER_CONNECT 4 /* - struct curltime */
|
||||
#define CF_QUERY_TIMER_APPCONNECT 5 /* - struct curltime */
|
||||
|
||||
/**
|
||||
* Query the cfilter for properties. Filters ignorant of a query will
|
||||
* pass it "down" the filter chain.
|
||||
*/
|
||||
typedef CURLcode Curl_cft_query(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
int query, int *pres1, void *pres2);
|
||||
|
||||
/**
|
||||
* Type flags for connection filters. A filter can have none, one or
|
||||
* many of those. Use to evaluate state/capabilities of a filter chain.
|
||||
*
|
||||
* CF_TYPE_IP_CONNECT: provides an IP connection or sth equivalent, like
|
||||
* a CONNECT tunnel, a UNIX domain socket, a QUIC
|
||||
* connection, etc.
|
||||
* CF_TYPE_SSL: provide SSL/TLS
|
||||
* CF_TYPE_MULTIPLEX: provides multiplexing of easy handles
|
||||
*/
|
||||
#define CF_TYPE_IP_CONNECT (1 << 0)
|
||||
#define CF_TYPE_SSL (1 << 1)
|
||||
#define CF_TYPE_MULTIPLEX (1 << 2)
|
||||
|
||||
/* A connection filter type, e.g. specific implementation. */
|
||||
struct Curl_cftype {
|
||||
const char *name; /* name of the filter type */
|
||||
int flags; /* flags of filter type */
|
||||
int log_level; /* log level for such filters */
|
||||
Curl_cft_destroy_this *destroy; /* destroy resources of this cf */
|
||||
Curl_cft_connect *connect; /* establish connection */
|
||||
Curl_cft_close *close; /* close conn */
|
||||
Curl_cft_get_host *get_host; /* host filter talks to */
|
||||
Curl_cft_get_select_socks *get_select_socks;/* sockets to select on */
|
||||
Curl_cft_data_pending *has_data_pending;/* conn has data pending */
|
||||
Curl_cft_send *do_send; /* send data */
|
||||
Curl_cft_recv *do_recv; /* receive data */
|
||||
Curl_cft_cntrl *cntrl; /* events/control */
|
||||
Curl_cft_conn_is_alive *is_alive; /* FALSE if conn is dead, Jim! */
|
||||
Curl_cft_conn_keep_alive *keep_alive; /* try to keep it alive */
|
||||
Curl_cft_query *query; /* query filter chain */
|
||||
};
|
||||
|
||||
/* A connection filter instance, e.g. registered at a connection */
|
||||
struct Curl_cfilter {
|
||||
const struct Curl_cftype *cft; /* the type providing implementation */
|
||||
struct Curl_cfilter *next; /* next filter in chain */
|
||||
void *ctx; /* filter type specific settings */
|
||||
struct connectdata *conn; /* the connection this filter belongs to */
|
||||
int sockindex; /* the index the filter is installed at */
|
||||
BIT(connected); /* != 0 iff this filter is connected */
|
||||
};
|
||||
|
||||
/* Default implementations for the type functions, implementing nop. */
|
||||
void Curl_cf_def_destroy_this(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data);
|
||||
|
||||
/* Default implementations for the type functions, implementing pass-through
|
||||
* the filter chain. */
|
||||
void Curl_cf_def_close(struct Curl_cfilter *cf, struct Curl_easy *data);
|
||||
CURLcode Curl_cf_def_connect(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool blocking, bool *done);
|
||||
void Curl_cf_def_get_host(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
const char **phost, const char **pdisplay_host,
|
||||
int *pport);
|
||||
int Curl_cf_def_get_select_socks(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
curl_socket_t *socks);
|
||||
bool Curl_cf_def_data_pending(struct Curl_cfilter *cf,
|
||||
const struct Curl_easy *data);
|
||||
ssize_t Curl_cf_def_send(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
const void *buf, size_t len, CURLcode *err);
|
||||
ssize_t Curl_cf_def_recv(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
char *buf, size_t len, CURLcode *err);
|
||||
CURLcode Curl_cf_def_cntrl(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
int event, int arg1, void *arg2);
|
||||
bool Curl_cf_def_conn_is_alive(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool *input_pending);
|
||||
CURLcode Curl_cf_def_conn_keep_alive(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data);
|
||||
CURLcode Curl_cf_def_query(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
int query, int *pres1, void *pres2);
|
||||
|
||||
/**
|
||||
* Create a new filter instance, unattached to the filter chain.
|
||||
* Use Curl_conn_cf_add() to add it to the chain.
|
||||
* @param pcf on success holds the created instance
|
||||
* @param cft the filter type
|
||||
* @param ctx the type specific context to use
|
||||
*/
|
||||
CURLcode Curl_cf_create(struct Curl_cfilter **pcf,
|
||||
const struct Curl_cftype *cft,
|
||||
void *ctx);
|
||||
|
||||
/**
|
||||
* Add a filter instance to the `sockindex` filter chain at connection
|
||||
* `conn`. The filter must not already be attached. It is inserted at
|
||||
* the start of the chain (top).
|
||||
*/
|
||||
void Curl_conn_cf_add(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
struct Curl_cfilter *cf);
|
||||
|
||||
/**
|
||||
* Insert a filter (chain) after `cf_at`.
|
||||
* `cf_new` must not already be attached.
|
||||
*/
|
||||
void Curl_conn_cf_insert_after(struct Curl_cfilter *cf_at,
|
||||
struct Curl_cfilter *cf_new);
|
||||
|
||||
/**
|
||||
* Discard, e.g. remove and destroy a specific filter instance.
|
||||
* If the filter is attached to a connection, it will be removed before
|
||||
* it is destroyed.
|
||||
*/
|
||||
void Curl_conn_cf_discard(struct Curl_cfilter *cf, struct Curl_easy *data);
|
||||
|
||||
/**
|
||||
* Discard all cfilters starting with `*pcf` and clearing it afterwards.
|
||||
*/
|
||||
void Curl_conn_cf_discard_chain(struct Curl_cfilter **pcf,
|
||||
struct Curl_easy *data);
|
||||
|
||||
/**
|
||||
* Remove and destroy all filters at chain `sockindex` on connection `conn`.
|
||||
*/
|
||||
void Curl_conn_cf_discard_all(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex);
|
||||
|
||||
|
||||
CURLcode Curl_conn_cf_connect(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool blocking, bool *done);
|
||||
void Curl_conn_cf_close(struct Curl_cfilter *cf, struct Curl_easy *data);
|
||||
int Curl_conn_cf_get_select_socks(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
curl_socket_t *socks);
|
||||
bool Curl_conn_cf_data_pending(struct Curl_cfilter *cf,
|
||||
const struct Curl_easy *data);
|
||||
ssize_t Curl_conn_cf_send(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
const void *buf, size_t len, CURLcode *err);
|
||||
ssize_t Curl_conn_cf_recv(struct Curl_cfilter *cf, struct Curl_easy *data,
|
||||
char *buf, size_t len, CURLcode *err);
|
||||
CURLcode Curl_conn_cf_cntrl(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data,
|
||||
bool ignore_result,
|
||||
int event, int arg1, void *arg2);
|
||||
|
||||
/**
|
||||
* Get the socket used by the filter chain starting at `cf`.
|
||||
* Returns CURL_SOCKET_BAD if not available.
|
||||
*/
|
||||
curl_socket_t Curl_conn_cf_get_socket(struct Curl_cfilter *cf,
|
||||
struct Curl_easy *data);
|
||||
|
||||
|
||||
#define CURL_CF_SSL_DEFAULT -1
|
||||
#define CURL_CF_SSL_DISABLE 0
|
||||
#define CURL_CF_SSL_ENABLE 1
|
||||
|
||||
/**
|
||||
* Bring the filter chain at `sockindex` for connection `data->conn` into
|
||||
* connected state. Which will set `*done` to TRUE.
|
||||
* This can be called on an already connected chain with no side effects.
|
||||
* When not `blocking`, calls may return without error and `*done != TRUE`,
|
||||
* while the individual filters negotiated the connection.
|
||||
*/
|
||||
CURLcode Curl_conn_connect(struct Curl_easy *data, int sockindex,
|
||||
bool blocking, bool *done);
|
||||
|
||||
/**
|
||||
* Check if the filter chain at `sockindex` for connection `conn` is
|
||||
* completely connected.
|
||||
*/
|
||||
bool Curl_conn_is_connected(struct connectdata *conn, int sockindex);
|
||||
|
||||
/**
|
||||
* Determine if we have reached the remote host on IP level, e.g.
|
||||
* have a TCP connection. This turns TRUE before a possible SSL
|
||||
* handshake has been started/done.
|
||||
*/
|
||||
bool Curl_conn_is_ip_connected(struct Curl_easy *data, int sockindex);
|
||||
|
||||
/**
|
||||
* Determine if the connection is using SSL to the remote host
|
||||
* (or will be once connected). This will return FALSE, if SSL
|
||||
* is only used in proxying and not for the tunnel itself.
|
||||
*/
|
||||
bool Curl_conn_is_ssl(struct connectdata *conn, int sockindex);
|
||||
|
||||
/**
|
||||
* Connection provides multiplexing of easy handles at `socketindex`.
|
||||
*/
|
||||
bool Curl_conn_is_multiplex(struct connectdata *conn, int sockindex);
|
||||
|
||||
/**
|
||||
* Close the filter chain at `sockindex` for connection `data->conn`.
|
||||
* Filters remain in place and may be connected again afterwards.
|
||||
*/
|
||||
void Curl_conn_close(struct Curl_easy *data, int sockindex);
|
||||
|
||||
/**
|
||||
* Return if data is pending in some connection filter at chain
|
||||
* `sockindex` for connection `data->conn`.
|
||||
*/
|
||||
bool Curl_conn_data_pending(struct Curl_easy *data,
|
||||
int sockindex);
|
||||
|
||||
/**
|
||||
* Return the socket used on data's connection for the index.
|
||||
* Returns CURL_SOCKET_BAD if not available.
|
||||
*/
|
||||
curl_socket_t Curl_conn_get_socket(struct Curl_easy *data, int sockindex);
|
||||
|
||||
/**
|
||||
* Get any select fd flags and the socket filters at chain `sockindex`
|
||||
* at connection `conn` might be waiting for.
|
||||
*/
|
||||
int Curl_conn_get_select_socks(struct Curl_easy *data, int sockindex,
|
||||
curl_socket_t *socks);
|
||||
|
||||
/**
|
||||
* Receive data through the filter chain at `sockindex` for connection
|
||||
* `data->conn`. Copy at most `len` bytes into `buf`. Return the
|
||||
* actuel number of bytes copied or a negative value on error.
|
||||
* The error code is placed into `*code`.
|
||||
*/
|
||||
ssize_t Curl_conn_recv(struct Curl_easy *data, int sockindex, char *buf,
|
||||
size_t len, CURLcode *code);
|
||||
|
||||
/**
|
||||
* Send `len` bytes of data from `buf` through the filter chain `sockindex`
|
||||
* at connection `data->conn`. Return the actual number of bytes written
|
||||
* or a negative value on error.
|
||||
* The error code is placed into `*code`.
|
||||
*/
|
||||
ssize_t Curl_conn_send(struct Curl_easy *data, int sockindex,
|
||||
const void *buf, size_t len, CURLcode *code);
|
||||
|
||||
/**
|
||||
* The easy handle `data` is being attached to `conn`. This does
|
||||
* not mean that data will actually do a transfer. Attachment is
|
||||
* also used for temporary actions on the connection.
|
||||
*/
|
||||
void Curl_conn_ev_data_attach(struct connectdata *conn,
|
||||
struct Curl_easy *data);
|
||||
|
||||
/**
|
||||
* The easy handle `data` is being detached (no longer served)
|
||||
* by connection `conn`. All filters are informed to release any resources
|
||||
* related to `data`.
|
||||
* Note: there may be several `data` attached to a connection at the same
|
||||
* time.
|
||||
*/
|
||||
void Curl_conn_ev_data_detach(struct connectdata *conn,
|
||||
struct Curl_easy *data);
|
||||
|
||||
/**
|
||||
* Notify connection filters that they need to setup data for
|
||||
* a transfer.
|
||||
*/
|
||||
CURLcode Curl_conn_ev_data_setup(struct Curl_easy *data);
|
||||
|
||||
/**
|
||||
* Notify connection filters that now would be a good time to
|
||||
* perform any idle, e.g. time related, actions.
|
||||
*/
|
||||
CURLcode Curl_conn_ev_data_idle(struct Curl_easy *data);
|
||||
|
||||
/**
|
||||
* Notify connection filters that the transfer represented by `data`
|
||||
* is donw with sending data (e.g. has uploaded everything).
|
||||
*/
|
||||
void Curl_conn_ev_data_done_send(struct Curl_easy *data);
|
||||
|
||||
/**
|
||||
* Notify connection filters that the transfer represented by `data`
|
||||
* is finished - eventually premature, e.g. before being complete.
|
||||
*/
|
||||
void Curl_conn_ev_data_done(struct Curl_easy *data, bool premature);
|
||||
|
||||
/**
|
||||
* Notify connection filters that the transfer of data is paused/unpaused.
|
||||
*/
|
||||
CURLcode Curl_conn_ev_data_pause(struct Curl_easy *data, bool do_pause);
|
||||
|
||||
/**
|
||||
* Inform connection filters to update their info in `conn`.
|
||||
*/
|
||||
void Curl_conn_ev_update_info(struct Curl_easy *data,
|
||||
struct connectdata *conn);
|
||||
|
||||
/**
|
||||
* Update connection statistics
|
||||
*/
|
||||
void Curl_conn_report_connect_stats(struct Curl_easy *data,
|
||||
struct connectdata *conn);
|
||||
|
||||
/**
|
||||
* Check if FIRSTSOCKET's cfilter chain deems connection alive.
|
||||
*/
|
||||
bool Curl_conn_is_alive(struct Curl_easy *data, struct connectdata *conn,
|
||||
bool *input_pending);
|
||||
|
||||
/**
|
||||
* Try to upkeep the connection filters at sockindex.
|
||||
*/
|
||||
CURLcode Curl_conn_keep_alive(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex);
|
||||
|
||||
void Curl_conn_get_host(struct Curl_easy *data, int sockindex,
|
||||
const char **phost, const char **pdisplay_host,
|
||||
int *pport);
|
||||
|
||||
/**
|
||||
* Get the maximum number of parallel transfers the connection
|
||||
* expects to be able to handle at `sockindex`.
|
||||
*/
|
||||
size_t Curl_conn_get_max_concurrent(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex);
|
||||
|
||||
|
||||
/**
|
||||
* Types and macros used to keep the current easy handle in filter calls,
|
||||
* allowing for nested invocations. See #10336.
|
||||
*
|
||||
* `cf_call_data` is intended to be a member of the cfilter's `ctx` type.
|
||||
* A filter defines the macro `CF_CTX_CALL_DATA` to give access to that.
|
||||
*
|
||||
* With all values 0, the default, this indicates that there is no cfilter
|
||||
* call with `data` ongoing.
|
||||
* Macro `CF_DATA_SAVE` preserves the current `cf_call_data` in a local
|
||||
* variable and sets the `data` given, incrementing the `depth` counter.
|
||||
*
|
||||
* Macro `CF_DATA_RESTORE` restores the old values from the local variable,
|
||||
* while checking that `depth` values are as expected (debug build), catching
|
||||
* cases where a "lower" RESTORE was not called.
|
||||
*
|
||||
* Finally, macro `CF_DATA_CURRENT` gives the easy handle of the current
|
||||
* invocation.
|
||||
*/
|
||||
struct cf_call_data {
|
||||
struct Curl_easy *data;
|
||||
#ifdef DEBUGBUILD
|
||||
int depth;
|
||||
#endif
|
||||
};
|
||||
|
||||
/**
|
||||
* define to access the `struct cf_call_data for a cfilter. Normally
|
||||
* a member in the cfilter's `ctx`.
|
||||
*
|
||||
* #define CF_CTX_CALL_DATA(cf) -> struct cf_call_data instance
|
||||
*/
|
||||
|
||||
#ifdef DEBUGBUILD
|
||||
|
||||
#define CF_DATA_SAVE(save, cf, data) \
|
||||
do { \
|
||||
(save) = CF_CTX_CALL_DATA(cf); \
|
||||
DEBUGASSERT((save).data == NULL || (save).depth > 0); \
|
||||
CF_CTX_CALL_DATA(cf).depth++; \
|
||||
CF_CTX_CALL_DATA(cf).data = (struct Curl_easy *)data; \
|
||||
} while(0)
|
||||
|
||||
#define CF_DATA_RESTORE(cf, save) \
|
||||
do { \
|
||||
DEBUGASSERT(CF_CTX_CALL_DATA(cf).depth == (save).depth + 1); \
|
||||
DEBUGASSERT((save).data == NULL || (save).depth > 0); \
|
||||
CF_CTX_CALL_DATA(cf) = (save); \
|
||||
} while(0)
|
||||
|
||||
#else /* DEBUGBUILD */
|
||||
|
||||
#define CF_DATA_SAVE(save, cf, data) \
|
||||
do { \
|
||||
(save) = CF_CTX_CALL_DATA(cf); \
|
||||
CF_CTX_CALL_DATA(cf).data = (struct Curl_easy *)data; \
|
||||
} while(0)
|
||||
|
||||
#define CF_DATA_RESTORE(cf, save) \
|
||||
do { \
|
||||
CF_CTX_CALL_DATA(cf) = (save); \
|
||||
} while(0)
|
||||
|
||||
#endif /* !DEBUGBUILD */
|
||||
|
||||
#define CF_DATA_CURRENT(cf) \
|
||||
((cf)? (CF_CTX_CALL_DATA(cf).data) : NULL)
|
||||
|
||||
#endif /* HEADER_CURL_CFILTERS_H */
|
|
@ -5,12 +5,12 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2012 - 2016, Linus Nielsen Feltzing, <linus@haxx.se>
|
||||
* Copyright (C) 2012 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Linus Nielsen Feltzing, <linus@haxx.se>
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -19,6 +19,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -34,92 +36,61 @@
|
|||
#include "share.h"
|
||||
#include "sigpipe.h"
|
||||
#include "connect.h"
|
||||
#include "strcase.h"
|
||||
|
||||
/* The last 3 #include files should be in this order */
|
||||
#include "curl_printf.h"
|
||||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
#ifdef CURLDEBUG
|
||||
/* the debug versions of these macros make extra certain that the lock is
|
||||
never doubly locked or unlocked */
|
||||
#define CONN_LOCK(x) if((x)->share) { \
|
||||
Curl_share_lock((x), CURL_LOCK_DATA_CONNECT, CURL_LOCK_ACCESS_SINGLE); \
|
||||
DEBUGASSERT(!(x)->state.conncache_lock); \
|
||||
(x)->state.conncache_lock = TRUE; \
|
||||
}
|
||||
#define HASHKEY_SIZE 128
|
||||
|
||||
#define CONN_UNLOCK(x) if((x)->share) { \
|
||||
DEBUGASSERT((x)->state.conncache_lock); \
|
||||
(x)->state.conncache_lock = FALSE; \
|
||||
Curl_share_unlock((x), CURL_LOCK_DATA_CONNECT); \
|
||||
}
|
||||
#else
|
||||
#define CONN_LOCK(x) if((x)->share) \
|
||||
Curl_share_lock((x), CURL_LOCK_DATA_CONNECT, CURL_LOCK_ACCESS_SINGLE)
|
||||
#define CONN_UNLOCK(x) if((x)->share) \
|
||||
Curl_share_unlock((x), CURL_LOCK_DATA_CONNECT)
|
||||
#endif
|
||||
|
||||
static void conn_llist_dtor(void *user, void *element)
|
||||
static CURLcode bundle_create(struct connectbundle **bundlep)
|
||||
{
|
||||
struct connectdata *conn = element;
|
||||
(void)user;
|
||||
conn->bundle = NULL;
|
||||
}
|
||||
|
||||
static CURLcode bundle_create(struct Curl_easy *data,
|
||||
struct connectbundle **cb_ptr)
|
||||
{
|
||||
(void)data;
|
||||
DEBUGASSERT(*cb_ptr == NULL);
|
||||
*cb_ptr = malloc(sizeof(struct connectbundle));
|
||||
if(!*cb_ptr)
|
||||
DEBUGASSERT(*bundlep == NULL);
|
||||
*bundlep = malloc(sizeof(struct connectbundle));
|
||||
if(!*bundlep)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
||||
(*cb_ptr)->num_connections = 0;
|
||||
(*cb_ptr)->multiuse = BUNDLE_UNKNOWN;
|
||||
(*bundlep)->num_connections = 0;
|
||||
(*bundlep)->multiuse = BUNDLE_UNKNOWN;
|
||||
|
||||
Curl_llist_init(&(*cb_ptr)->conn_list, (curl_llist_dtor) conn_llist_dtor);
|
||||
Curl_llist_init(&(*bundlep)->conn_list, NULL);
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
static void bundle_destroy(struct connectbundle *cb_ptr)
|
||||
static void bundle_destroy(struct connectbundle *bundle)
|
||||
{
|
||||
if(!cb_ptr)
|
||||
return;
|
||||
|
||||
Curl_llist_destroy(&cb_ptr->conn_list, NULL);
|
||||
|
||||
free(cb_ptr);
|
||||
free(bundle);
|
||||
}
|
||||
|
||||
/* Add a connection to a bundle */
|
||||
static void bundle_add_conn(struct connectbundle *cb_ptr,
|
||||
static void bundle_add_conn(struct connectbundle *bundle,
|
||||
struct connectdata *conn)
|
||||
{
|
||||
Curl_llist_insert_next(&cb_ptr->conn_list, cb_ptr->conn_list.tail, conn,
|
||||
Curl_llist_insert_next(&bundle->conn_list, bundle->conn_list.tail, conn,
|
||||
&conn->bundle_node);
|
||||
conn->bundle = cb_ptr;
|
||||
cb_ptr->num_connections++;
|
||||
conn->bundle = bundle;
|
||||
bundle->num_connections++;
|
||||
}
|
||||
|
||||
/* Remove a connection from a bundle */
|
||||
static int bundle_remove_conn(struct connectbundle *cb_ptr,
|
||||
static int bundle_remove_conn(struct connectbundle *bundle,
|
||||
struct connectdata *conn)
|
||||
{
|
||||
struct curl_llist_element *curr;
|
||||
struct Curl_llist_element *curr;
|
||||
|
||||
curr = cb_ptr->conn_list.head;
|
||||
curr = bundle->conn_list.head;
|
||||
while(curr) {
|
||||
if(curr->ptr == conn) {
|
||||
Curl_llist_remove(&cb_ptr->conn_list, curr, NULL);
|
||||
cb_ptr->num_connections--;
|
||||
Curl_llist_remove(&bundle->conn_list, curr, NULL);
|
||||
bundle->num_connections--;
|
||||
conn->bundle = NULL;
|
||||
return 1; /* we removed a handle */
|
||||
}
|
||||
curr = curr->next;
|
||||
}
|
||||
DEBUGASSERT(0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -132,23 +103,16 @@ static void free_bundle_hash_entry(void *freethis)
|
|||
|
||||
int Curl_conncache_init(struct conncache *connc, int size)
|
||||
{
|
||||
int rc;
|
||||
|
||||
/* allocate a new easy handle to use when closing cached connections */
|
||||
connc->closure_handle = curl_easy_init();
|
||||
if(!connc->closure_handle)
|
||||
return 1; /* bad */
|
||||
|
||||
rc = Curl_hash_init(&connc->hash, size, Curl_hash_str,
|
||||
Curl_str_key_compare, free_bundle_hash_entry);
|
||||
if(rc) {
|
||||
Curl_close(connc->closure_handle);
|
||||
connc->closure_handle = NULL;
|
||||
}
|
||||
else
|
||||
connc->closure_handle->state.conn_cache = connc;
|
||||
Curl_hash_init(&connc->hash, size, Curl_hash_str,
|
||||
Curl_str_key_compare, free_bundle_hash_entry);
|
||||
connc->closure_handle->state.conn_cache = connc;
|
||||
|
||||
return rc;
|
||||
return 0; /* good */
|
||||
}
|
||||
|
||||
void Curl_conncache_destroy(struct conncache *connc)
|
||||
|
@ -158,29 +122,30 @@ void Curl_conncache_destroy(struct conncache *connc)
|
|||
}
|
||||
|
||||
/* creates a key to find a bundle for this connection */
|
||||
static void hashkey(struct connectdata *conn, char *buf,
|
||||
size_t len) /* something like 128 is fine */
|
||||
static void hashkey(struct connectdata *conn, char *buf, size_t len)
|
||||
{
|
||||
const char *hostname;
|
||||
|
||||
if(conn->bits.socksproxy)
|
||||
hostname = conn->socks_proxy.host.name;
|
||||
else if(conn->bits.httpproxy)
|
||||
long port = conn->remote_port;
|
||||
DEBUGASSERT(len >= HASHKEY_SIZE);
|
||||
#ifndef CURL_DISABLE_PROXY
|
||||
if(conn->bits.httpproxy && !conn->bits.tunnel_proxy) {
|
||||
hostname = conn->http_proxy.host.name;
|
||||
else if(conn->bits.conn_to_host)
|
||||
hostname = conn->conn_to_host.name;
|
||||
port = conn->port;
|
||||
}
|
||||
else
|
||||
#endif
|
||||
if(conn->bits.conn_to_host)
|
||||
hostname = conn->conn_to_host.name;
|
||||
else
|
||||
hostname = conn->host.name;
|
||||
|
||||
DEBUGASSERT(len > 32);
|
||||
|
||||
/* put the number first so that the hostname gets cut off if too long */
|
||||
msnprintf(buf, len, "%ld%s", conn->port, hostname);
|
||||
}
|
||||
|
||||
void Curl_conncache_unlock(struct Curl_easy *data)
|
||||
{
|
||||
CONN_UNLOCK(data);
|
||||
/* put the numbers first so that the hostname gets cut off if too long */
|
||||
#ifdef ENABLE_IPV6
|
||||
msnprintf(buf, len, "%u/%ld/%s", conn->scope_id, port, hostname);
|
||||
#else
|
||||
msnprintf(buf, len, "%ld/%s", port, hostname);
|
||||
#endif
|
||||
Curl_strntolower(buf, buf, len);
|
||||
}
|
||||
|
||||
/* Returns number of connections currently held in the connection cache.
|
||||
|
@ -189,21 +154,9 @@ void Curl_conncache_unlock(struct Curl_easy *data)
|
|||
size_t Curl_conncache_size(struct Curl_easy *data)
|
||||
{
|
||||
size_t num;
|
||||
CONN_LOCK(data);
|
||||
CONNCACHE_LOCK(data);
|
||||
num = data->state.conn_cache->num_conn;
|
||||
CONN_UNLOCK(data);
|
||||
return num;
|
||||
}
|
||||
|
||||
/* Returns number of connections currently held in the connections's bundle
|
||||
Locks/unlocks the cache itself!
|
||||
*/
|
||||
size_t Curl_conncache_bundle_size(struct connectdata *conn)
|
||||
{
|
||||
size_t num;
|
||||
CONN_LOCK(conn->data);
|
||||
num = conn->bundle->num_connections;
|
||||
CONN_UNLOCK(conn->data);
|
||||
CONNCACHE_UNLOCK(data);
|
||||
return num;
|
||||
}
|
||||
|
||||
|
@ -211,13 +164,15 @@ size_t Curl_conncache_bundle_size(struct connectdata *conn)
|
|||
connectdata struct is setup to use.
|
||||
|
||||
**NOTE**: When it returns, it holds the connection cache lock! */
|
||||
struct connectbundle *Curl_conncache_find_bundle(struct connectdata *conn,
|
||||
struct conncache *connc)
|
||||
struct connectbundle *
|
||||
Curl_conncache_find_bundle(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
struct conncache *connc)
|
||||
{
|
||||
struct connectbundle *bundle = NULL;
|
||||
CONN_LOCK(conn->data);
|
||||
CONNCACHE_LOCK(data);
|
||||
if(connc) {
|
||||
char key[128];
|
||||
char key[HASHKEY_SIZE];
|
||||
hashkey(conn, key, sizeof(key));
|
||||
bundle = Curl_hash_pick(&connc->hash, key, strlen(key));
|
||||
}
|
||||
|
@ -225,20 +180,18 @@ struct connectbundle *Curl_conncache_find_bundle(struct connectdata *conn,
|
|||
return bundle;
|
||||
}
|
||||
|
||||
static bool conncache_add_bundle(struct conncache *connc,
|
||||
char *key,
|
||||
struct connectbundle *bundle)
|
||||
static void *conncache_add_bundle(struct conncache *connc,
|
||||
char *key,
|
||||
struct connectbundle *bundle)
|
||||
{
|
||||
void *p = Curl_hash_add(&connc->hash, key, strlen(key), bundle);
|
||||
|
||||
return p?TRUE:FALSE;
|
||||
return Curl_hash_add(&connc->hash, key, strlen(key), bundle);
|
||||
}
|
||||
|
||||
static void conncache_remove_bundle(struct conncache *connc,
|
||||
struct connectbundle *bundle)
|
||||
{
|
||||
struct curl_hash_iterator iter;
|
||||
struct curl_hash_element *he;
|
||||
struct Curl_hash_iterator iter;
|
||||
struct Curl_hash_element *he;
|
||||
|
||||
if(!connc)
|
||||
return;
|
||||
|
@ -258,54 +211,53 @@ static void conncache_remove_bundle(struct conncache *connc,
|
|||
}
|
||||
}
|
||||
|
||||
CURLcode Curl_conncache_add_conn(struct conncache *connc,
|
||||
struct connectdata *conn)
|
||||
CURLcode Curl_conncache_add_conn(struct Curl_easy *data)
|
||||
{
|
||||
CURLcode result = CURLE_OK;
|
||||
struct connectbundle *bundle;
|
||||
struct connectbundle *new_bundle = NULL;
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct connectbundle *bundle = NULL;
|
||||
struct connectdata *conn = data->conn;
|
||||
struct conncache *connc = data->state.conn_cache;
|
||||
DEBUGASSERT(conn);
|
||||
|
||||
/* *find_bundle() locks the connection cache */
|
||||
bundle = Curl_conncache_find_bundle(conn, data->state.conn_cache);
|
||||
bundle = Curl_conncache_find_bundle(data, conn, data->state.conn_cache);
|
||||
if(!bundle) {
|
||||
int rc;
|
||||
char key[128];
|
||||
char key[HASHKEY_SIZE];
|
||||
|
||||
result = bundle_create(data, &new_bundle);
|
||||
result = bundle_create(&bundle);
|
||||
if(result) {
|
||||
goto unlock;
|
||||
}
|
||||
|
||||
hashkey(conn, key, sizeof(key));
|
||||
rc = conncache_add_bundle(data->state.conn_cache, key, new_bundle);
|
||||
|
||||
if(!rc) {
|
||||
bundle_destroy(new_bundle);
|
||||
if(!conncache_add_bundle(data->state.conn_cache, key, bundle)) {
|
||||
bundle_destroy(bundle);
|
||||
result = CURLE_OUT_OF_MEMORY;
|
||||
goto unlock;
|
||||
}
|
||||
bundle = new_bundle;
|
||||
}
|
||||
|
||||
bundle_add_conn(bundle, conn);
|
||||
conn->connection_id = connc->next_connection_id++;
|
||||
connc->num_conn++;
|
||||
|
||||
DEBUGF(infof(conn->data, "Added connection %ld. "
|
||||
"The cache now contains %zu members\n",
|
||||
DEBUGF(infof(data, "Added connection %ld. "
|
||||
"The cache now contains %zu members",
|
||||
conn->connection_id, connc->num_conn));
|
||||
|
||||
unlock:
|
||||
CONN_UNLOCK(data);
|
||||
CONNCACHE_UNLOCK(data);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/*
|
||||
* Removes the connectdata object from the connection cache *and* clears the
|
||||
* ->data pointer association. Pass TRUE/FALSE in the 'lock' argument
|
||||
* depending on if the parent function already holds the lock or not.
|
||||
* Removes the connectdata object from the connection cache, but the transfer
|
||||
* still owns this connection.
|
||||
*
|
||||
* Pass TRUE/FALSE in the 'lock' argument depending on if the parent function
|
||||
* already holds the lock or not.
|
||||
*/
|
||||
void Curl_conncache_remove_conn(struct Curl_easy *data,
|
||||
struct connectdata *conn, bool lock)
|
||||
|
@ -317,7 +269,7 @@ void Curl_conncache_remove_conn(struct Curl_easy *data,
|
|||
due to a failed connection attempt, before being added to a bundle */
|
||||
if(bundle) {
|
||||
if(lock) {
|
||||
CONN_LOCK(data);
|
||||
CONNCACHE_LOCK(data);
|
||||
}
|
||||
bundle_remove_conn(bundle, conn);
|
||||
if(bundle->num_connections == 0)
|
||||
|
@ -325,12 +277,11 @@ void Curl_conncache_remove_conn(struct Curl_easy *data,
|
|||
conn->bundle = NULL; /* removed from it */
|
||||
if(connc) {
|
||||
connc->num_conn--;
|
||||
DEBUGF(infof(data, "The cache now contains %zu members\n",
|
||||
DEBUGF(infof(data, "The cache now contains %zu members",
|
||||
connc->num_conn));
|
||||
}
|
||||
conn->data = NULL; /* clear the association */
|
||||
if(lock) {
|
||||
CONN_UNLOCK(data);
|
||||
CONNCACHE_UNLOCK(data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -350,16 +301,17 @@ void Curl_conncache_remove_conn(struct Curl_easy *data,
|
|||
bool Curl_conncache_foreach(struct Curl_easy *data,
|
||||
struct conncache *connc,
|
||||
void *param,
|
||||
int (*func)(struct connectdata *conn, void *param))
|
||||
int (*func)(struct Curl_easy *data,
|
||||
struct connectdata *conn, void *param))
|
||||
{
|
||||
struct curl_hash_iterator iter;
|
||||
struct curl_llist_element *curr;
|
||||
struct curl_hash_element *he;
|
||||
struct Curl_hash_iterator iter;
|
||||
struct Curl_llist_element *curr;
|
||||
struct Curl_hash_element *he;
|
||||
|
||||
if(!connc)
|
||||
return FALSE;
|
||||
|
||||
CONN_LOCK(data);
|
||||
CONNCACHE_LOCK(data);
|
||||
Curl_hash_start_iterate(&connc->hash, &iter);
|
||||
|
||||
he = Curl_hash_next_element(&iter);
|
||||
|
@ -376,13 +328,13 @@ bool Curl_conncache_foreach(struct Curl_easy *data,
|
|||
struct connectdata *conn = curr->ptr;
|
||||
curr = curr->next;
|
||||
|
||||
if(1 == func(conn, param)) {
|
||||
CONN_UNLOCK(data);
|
||||
if(1 == func(data, conn, param)) {
|
||||
CONNCACHE_UNLOCK(data);
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
CONN_UNLOCK(data);
|
||||
CONNCACHE_UNLOCK(data);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
@ -395,15 +347,15 @@ bool Curl_conncache_foreach(struct Curl_easy *data,
|
|||
static struct connectdata *
|
||||
conncache_find_first_connection(struct conncache *connc)
|
||||
{
|
||||
struct curl_hash_iterator iter;
|
||||
struct curl_hash_element *he;
|
||||
struct Curl_hash_iterator iter;
|
||||
struct Curl_hash_element *he;
|
||||
struct connectbundle *bundle;
|
||||
|
||||
Curl_hash_start_iterate(&connc->hash, &iter);
|
||||
|
||||
he = Curl_hash_next_element(&iter);
|
||||
while(he) {
|
||||
struct curl_llist_element *curr;
|
||||
struct Curl_llist_element *curr;
|
||||
bundle = he->ptr;
|
||||
|
||||
curr = bundle->conn_list.head;
|
||||
|
@ -423,26 +375,24 @@ conncache_find_first_connection(struct conncache *connc)
|
|||
*
|
||||
* Return TRUE if stored, FALSE if closed.
|
||||
*/
|
||||
bool Curl_conncache_return_conn(struct connectdata *conn)
|
||||
bool Curl_conncache_return_conn(struct Curl_easy *data,
|
||||
struct connectdata *conn)
|
||||
{
|
||||
struct Curl_easy *data = conn->data;
|
||||
|
||||
/* data->multi->maxconnects can be negative, deal with it. */
|
||||
size_t maxconnects =
|
||||
(data->multi->maxconnects < 0) ? data->multi->num_easy * 4:
|
||||
data->multi->maxconnects;
|
||||
struct connectdata *conn_candidate = NULL;
|
||||
|
||||
conn->data = NULL; /* no owner anymore */
|
||||
conn->lastused = Curl_now(); /* it was used up until now */
|
||||
if(maxconnects > 0 &&
|
||||
Curl_conncache_size(data) > maxconnects) {
|
||||
infof(data, "Connection cache is full, closing the oldest one.\n");
|
||||
infof(data, "Connection cache is full, closing the oldest one");
|
||||
|
||||
conn_candidate = Curl_conncache_extract_oldest(data);
|
||||
if(conn_candidate) {
|
||||
/* the winner gets the honour of being disconnected */
|
||||
(void)Curl_disconnect(data, conn_candidate, /* dead_connection */ FALSE);
|
||||
Curl_disconnect(data, conn_candidate, /* dead_connection */ FALSE);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -463,7 +413,7 @@ struct connectdata *
|
|||
Curl_conncache_extract_bundle(struct Curl_easy *data,
|
||||
struct connectbundle *bundle)
|
||||
{
|
||||
struct curl_llist_element *curr;
|
||||
struct Curl_llist_element *curr;
|
||||
timediff_t highscore = -1;
|
||||
timediff_t score;
|
||||
struct curltime now;
|
||||
|
@ -478,7 +428,7 @@ Curl_conncache_extract_bundle(struct Curl_easy *data,
|
|||
while(curr) {
|
||||
conn = curr->ptr;
|
||||
|
||||
if(!CONN_INUSE(conn) && !conn->data) {
|
||||
if(!CONN_INUSE(conn)) {
|
||||
/* Set higher score for the age passed since the connection was used */
|
||||
score = Curl_timediff(now, conn->lastused);
|
||||
|
||||
|
@ -493,9 +443,8 @@ Curl_conncache_extract_bundle(struct Curl_easy *data,
|
|||
/* remove it to prevent another thread from nicking it */
|
||||
bundle_remove_conn(bundle, conn_candidate);
|
||||
data->state.conn_cache->num_conn--;
|
||||
DEBUGF(infof(data, "The cache now contains %zu members\n",
|
||||
DEBUGF(infof(data, "The cache now contains %zu members",
|
||||
data->state.conn_cache->num_conn));
|
||||
conn_candidate->data = data; /* associate! */
|
||||
}
|
||||
|
||||
return conn_candidate;
|
||||
|
@ -511,9 +460,9 @@ struct connectdata *
|
|||
Curl_conncache_extract_oldest(struct Curl_easy *data)
|
||||
{
|
||||
struct conncache *connc = data->state.conn_cache;
|
||||
struct curl_hash_iterator iter;
|
||||
struct curl_llist_element *curr;
|
||||
struct curl_hash_element *he;
|
||||
struct Curl_hash_iterator iter;
|
||||
struct Curl_llist_element *curr;
|
||||
struct Curl_hash_element *he;
|
||||
timediff_t highscore =- 1;
|
||||
timediff_t score;
|
||||
struct curltime now;
|
||||
|
@ -523,7 +472,7 @@ Curl_conncache_extract_oldest(struct Curl_easy *data)
|
|||
|
||||
now = Curl_now();
|
||||
|
||||
CONN_LOCK(data);
|
||||
CONNCACHE_LOCK(data);
|
||||
Curl_hash_start_iterate(&connc->hash, &iter);
|
||||
|
||||
he = Curl_hash_next_element(&iter);
|
||||
|
@ -536,7 +485,8 @@ Curl_conncache_extract_oldest(struct Curl_easy *data)
|
|||
while(curr) {
|
||||
conn = curr->ptr;
|
||||
|
||||
if(!CONN_INUSE(conn) && !conn->data) {
|
||||
if(!CONN_INUSE(conn) && !conn->bits.close &&
|
||||
!conn->connect_only) {
|
||||
/* Set higher score for the age passed since the connection was used */
|
||||
score = Curl_timediff(now, conn->lastused);
|
||||
|
||||
|
@ -555,11 +505,10 @@ Curl_conncache_extract_oldest(struct Curl_easy *data)
|
|||
/* remove it to prevent another thread from nicking it */
|
||||
bundle_remove_conn(bundle_candidate, conn_candidate);
|
||||
connc->num_conn--;
|
||||
DEBUGF(infof(data, "The cache now contains %zu members\n",
|
||||
DEBUGF(infof(data, "The cache now contains %zu members",
|
||||
connc->num_conn));
|
||||
conn_candidate->data = data; /* associate! */
|
||||
}
|
||||
CONN_UNLOCK(data);
|
||||
CONNCACHE_UNLOCK(data);
|
||||
|
||||
return conn_candidate;
|
||||
}
|
||||
|
@ -567,39 +516,41 @@ Curl_conncache_extract_oldest(struct Curl_easy *data)
|
|||
void Curl_conncache_close_all_connections(struct conncache *connc)
|
||||
{
|
||||
struct connectdata *conn;
|
||||
char buffer[READBUFFER_MIN + 1];
|
||||
SIGPIPE_VARIABLE(pipe_st);
|
||||
if(!connc->closure_handle)
|
||||
return;
|
||||
connc->closure_handle->state.buffer = buffer;
|
||||
connc->closure_handle->set.buffer_size = READBUFFER_MIN;
|
||||
|
||||
conn = conncache_find_first_connection(connc);
|
||||
while(conn) {
|
||||
SIGPIPE_VARIABLE(pipe_st);
|
||||
conn->data = connc->closure_handle;
|
||||
|
||||
sigpipe_ignore(conn->data, &pipe_st);
|
||||
sigpipe_ignore(connc->closure_handle, &pipe_st);
|
||||
/* This will remove the connection from the cache */
|
||||
connclose(conn, "kill all");
|
||||
(void)Curl_disconnect(connc->closure_handle, conn, FALSE);
|
||||
Curl_conncache_remove_conn(connc->closure_handle, conn, TRUE);
|
||||
Curl_disconnect(connc->closure_handle, conn, FALSE);
|
||||
sigpipe_restore(&pipe_st);
|
||||
|
||||
conn = conncache_find_first_connection(connc);
|
||||
}
|
||||
|
||||
if(connc->closure_handle) {
|
||||
SIGPIPE_VARIABLE(pipe_st);
|
||||
sigpipe_ignore(connc->closure_handle, &pipe_st);
|
||||
connc->closure_handle->state.buffer = NULL;
|
||||
sigpipe_ignore(connc->closure_handle, &pipe_st);
|
||||
|
||||
Curl_hostcache_clean(connc->closure_handle,
|
||||
connc->closure_handle->dns.hostcache);
|
||||
Curl_close(connc->closure_handle);
|
||||
sigpipe_restore(&pipe_st);
|
||||
}
|
||||
Curl_hostcache_clean(connc->closure_handle,
|
||||
connc->closure_handle->dns.hostcache);
|
||||
Curl_close(&connc->closure_handle);
|
||||
sigpipe_restore(&pipe_st);
|
||||
}
|
||||
|
||||
#if 0
|
||||
/* Useful for debugging the connection cache */
|
||||
void Curl_conncache_print(struct conncache *connc)
|
||||
{
|
||||
struct curl_hash_iterator iter;
|
||||
struct curl_llist_element *curr;
|
||||
struct curl_hash_element *he;
|
||||
struct Curl_hash_iterator iter;
|
||||
struct Curl_llist_element *curr;
|
||||
struct Curl_hash_element *he;
|
||||
|
||||
if(!connc)
|
||||
return;
|
||||
|
|
|
@ -7,12 +7,12 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2015 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) 2012 - 2014, Linus Nielsen Feltzing, <linus@haxx.se>
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Linus Nielsen Feltzing, <linus@haxx.se>
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -21,6 +21,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/*
|
||||
|
@ -29,8 +31,13 @@
|
|||
* be shared.
|
||||
*/
|
||||
|
||||
#include <curl/curl.h>
|
||||
#include "timeval.h"
|
||||
|
||||
struct connectdata;
|
||||
|
||||
struct conncache {
|
||||
struct curl_hash hash;
|
||||
struct Curl_hash hash;
|
||||
size_t num_conn;
|
||||
long next_connection_id;
|
||||
struct curltime last_cleanup;
|
||||
|
@ -42,10 +49,38 @@ struct conncache {
|
|||
#define BUNDLE_UNKNOWN 0 /* initial value */
|
||||
#define BUNDLE_MULTIPLEX 2
|
||||
|
||||
#ifdef CURLDEBUG
|
||||
/* the debug versions of these macros make extra certain that the lock is
|
||||
never doubly locked or unlocked */
|
||||
#define CONNCACHE_LOCK(x) \
|
||||
do { \
|
||||
if((x)->share) { \
|
||||
Curl_share_lock((x), CURL_LOCK_DATA_CONNECT, \
|
||||
CURL_LOCK_ACCESS_SINGLE); \
|
||||
DEBUGASSERT(!(x)->state.conncache_lock); \
|
||||
(x)->state.conncache_lock = TRUE; \
|
||||
} \
|
||||
} while(0)
|
||||
|
||||
#define CONNCACHE_UNLOCK(x) \
|
||||
do { \
|
||||
if((x)->share) { \
|
||||
DEBUGASSERT((x)->state.conncache_lock); \
|
||||
(x)->state.conncache_lock = FALSE; \
|
||||
Curl_share_unlock((x), CURL_LOCK_DATA_CONNECT); \
|
||||
} \
|
||||
} while(0)
|
||||
#else
|
||||
#define CONNCACHE_LOCK(x) if((x)->share) \
|
||||
Curl_share_lock((x), CURL_LOCK_DATA_CONNECT, CURL_LOCK_ACCESS_SINGLE)
|
||||
#define CONNCACHE_UNLOCK(x) if((x)->share) \
|
||||
Curl_share_unlock((x), CURL_LOCK_DATA_CONNECT)
|
||||
#endif
|
||||
|
||||
struct connectbundle {
|
||||
int multiuse; /* supports multi-use */
|
||||
size_t num_connections; /* Number of connections in the bundle */
|
||||
struct curl_llist conn_list; /* The connectdata members of the bundle */
|
||||
struct Curl_llist conn_list; /* The connectdata members of the bundle */
|
||||
};
|
||||
|
||||
/* returns 1 on error, 0 is fine */
|
||||
|
@ -53,23 +88,23 @@ int Curl_conncache_init(struct conncache *, int size);
|
|||
void Curl_conncache_destroy(struct conncache *connc);
|
||||
|
||||
/* return the correct bundle, to a host or a proxy */
|
||||
struct connectbundle *Curl_conncache_find_bundle(struct connectdata *conn,
|
||||
struct connectbundle *Curl_conncache_find_bundle(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
struct conncache *connc);
|
||||
void Curl_conncache_unlock(struct Curl_easy *data);
|
||||
/* returns number of connections currently held in the connection cache */
|
||||
size_t Curl_conncache_size(struct Curl_easy *data);
|
||||
size_t Curl_conncache_bundle_size(struct connectdata *conn);
|
||||
|
||||
bool Curl_conncache_return_conn(struct connectdata *conn);
|
||||
CURLcode Curl_conncache_add_conn(struct conncache *connc,
|
||||
struct connectdata *conn) WARN_UNUSED_RESULT;
|
||||
bool Curl_conncache_return_conn(struct Curl_easy *data,
|
||||
struct connectdata *conn);
|
||||
CURLcode Curl_conncache_add_conn(struct Curl_easy *data) WARN_UNUSED_RESULT;
|
||||
void Curl_conncache_remove_conn(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
bool lock);
|
||||
bool Curl_conncache_foreach(struct Curl_easy *data,
|
||||
struct conncache *connc,
|
||||
void *param,
|
||||
int (*func)(struct connectdata *conn,
|
||||
int (*func)(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
void *param));
|
||||
|
||||
struct connectdata *
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
|
@ -27,12 +29,7 @@
|
|||
#include "sockaddr.h"
|
||||
#include "timeval.h"
|
||||
|
||||
CURLcode Curl_is_connected(struct connectdata *conn,
|
||||
int sockindex,
|
||||
bool *connected);
|
||||
|
||||
CURLcode Curl_connecthost(struct connectdata *conn,
|
||||
const struct Curl_dns_entry *host);
|
||||
struct Curl_dns_entry;
|
||||
|
||||
/* generic function that returns how much time there's left to run, according
|
||||
to the timeouts set */
|
||||
|
@ -51,60 +48,11 @@ timediff_t Curl_timeleft(struct Curl_easy *data,
|
|||
curl_socket_t Curl_getconnectinfo(struct Curl_easy *data,
|
||||
struct connectdata **connp);
|
||||
|
||||
/*
|
||||
* Check if a connection seems to be alive.
|
||||
*/
|
||||
bool Curl_connalive(struct connectdata *conn);
|
||||
bool Curl_addr2string(struct sockaddr *sa, curl_socklen_t salen,
|
||||
char *addr, int *port);
|
||||
|
||||
#ifdef USE_WINSOCK
|
||||
/* When you run a program that uses the Windows Sockets API, you may
|
||||
experience slow performance when you copy data to a TCP server.
|
||||
|
||||
https://support.microsoft.com/kb/823764
|
||||
|
||||
Work-around: Make the Socket Send Buffer Size Larger Than the Program Send
|
||||
Buffer Size
|
||||
|
||||
*/
|
||||
void Curl_sndbufset(curl_socket_t sockfd);
|
||||
#else
|
||||
#define Curl_sndbufset(y) Curl_nop_stmt
|
||||
#endif
|
||||
|
||||
void Curl_updateconninfo(struct connectdata *conn, curl_socket_t sockfd);
|
||||
void Curl_persistconninfo(struct connectdata *conn);
|
||||
int Curl_closesocket(struct connectdata *conn, curl_socket_t sock);
|
||||
|
||||
/*
|
||||
* The Curl_sockaddr_ex structure is basically libcurl's external API
|
||||
* curl_sockaddr structure with enough space available to directly hold any
|
||||
* protocol-specific address structures. The variable declared here will be
|
||||
* used to pass / receive data to/from the fopensocket callback if this has
|
||||
* been set, before that, it is initialized from parameters.
|
||||
*/
|
||||
struct Curl_sockaddr_ex {
|
||||
int family;
|
||||
int socktype;
|
||||
int protocol;
|
||||
unsigned int addrlen;
|
||||
union {
|
||||
struct sockaddr addr;
|
||||
struct Curl_sockaddr_storage buff;
|
||||
} _sa_ex_u;
|
||||
};
|
||||
#define sa_addr _sa_ex_u.addr
|
||||
|
||||
/*
|
||||
* Create a socket based on info from 'conn' and 'ai'.
|
||||
*
|
||||
* Fill in 'addr' and 'sockfd' accordingly if OK is returned. If the open
|
||||
* socket callback is set, used that!
|
||||
*
|
||||
*/
|
||||
CURLcode Curl_socket(struct connectdata *conn,
|
||||
const Curl_addrinfo *ai,
|
||||
struct Curl_sockaddr_ex *addr,
|
||||
curl_socket_t *sockfd);
|
||||
void Curl_persistconninfo(struct Curl_easy *data, struct connectdata *conn,
|
||||
char *local_ip, int local_port);
|
||||
|
||||
/*
|
||||
* Curl_conncontrol() marks the end of a connection/stream. The 'closeit'
|
||||
|
@ -139,6 +87,71 @@ void Curl_conncontrol(struct connectdata *conn,
|
|||
#define connkeep(x,y) Curl_conncontrol(x, CONNCTRL_KEEP)
|
||||
#endif
|
||||
|
||||
bool Curl_conn_data_pending(struct connectdata *conn, int sockindex);
|
||||
/**
|
||||
* Create a cfilter for making an "ip" connection to the
|
||||
* given address, using parameters from `conn`. The "ip" connection
|
||||
* can be a TCP socket, a UDP socket or even a QUIC connection.
|
||||
*
|
||||
* It MUST use only the supplied `ai` for its connection attempt.
|
||||
*
|
||||
* Such a filter may be used in "happy eyeball" scenarios, and its
|
||||
* `connect` implementation needs to support non-blocking. Once connected,
|
||||
* it MAY be installed in the connection filter chain to serve transfers.
|
||||
*/
|
||||
typedef CURLcode cf_ip_connect_create(struct Curl_cfilter **pcf,
|
||||
struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
const struct Curl_addrinfo *ai,
|
||||
int transport);
|
||||
|
||||
/**
|
||||
* Create a happy eyeball connection filter that uses the, once resolved,
|
||||
* address information to connect on ip families based on connection
|
||||
* configuration.
|
||||
* @param pcf output, the created cfilter
|
||||
* @param data easy handle used in creation
|
||||
* @param conn connection the filter is created for
|
||||
* @param cf_create method to create the sub-filters performing the
|
||||
* actual connects.
|
||||
*/
|
||||
CURLcode
|
||||
Curl_cf_happy_eyeballs_create(struct Curl_cfilter **pcf,
|
||||
struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
cf_ip_connect_create *cf_create,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
int transport);
|
||||
|
||||
CURLcode Curl_cf_setup_add(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
int transport,
|
||||
int ssl_mode);
|
||||
|
||||
CURLcode Curl_cf_setup_insert_after(struct Curl_cfilter *cf_at,
|
||||
struct Curl_easy *data,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
int transport,
|
||||
int ssl_mode);
|
||||
|
||||
/**
|
||||
* Setup the cfilters at `sockindex` in connection `conn`.
|
||||
* If no filter chain is installed yet, inspects the configuration
|
||||
* in `data` and `conn? to install a suitable filter chain.
|
||||
*/
|
||||
CURLcode Curl_conn_setup(struct Curl_easy *data,
|
||||
struct connectdata *conn,
|
||||
int sockindex,
|
||||
const struct Curl_dns_entry *remotehost,
|
||||
int ssl_mode);
|
||||
|
||||
extern struct Curl_cftype Curl_cft_happy_eyeballs;
|
||||
extern struct Curl_cftype Curl_cft_setup;
|
||||
|
||||
#ifdef DEBUGBUILD
|
||||
void Curl_debug_set_transport_provider(int transport,
|
||||
cf_ip_connect_create *cf_create);
|
||||
#endif
|
||||
|
||||
#endif /* HEADER_CURL_CONNECT_H */
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2018, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -26,16 +28,24 @@
|
|||
#include <curl/curl.h>
|
||||
#include <stddef.h>
|
||||
|
||||
#ifdef HAVE_ZLIB_H
|
||||
#ifdef HAVE_LIBZ
|
||||
#include <zlib.h>
|
||||
#ifdef __SYMBIAN32__
|
||||
/* zlib pollutes the namespace with this definition */
|
||||
#undef WIN32
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_BROTLI
|
||||
#if defined(__GNUC__)
|
||||
/* Ignore -Wvla warnings in brotli headers */
|
||||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Wvla"
|
||||
#endif
|
||||
#include <brotli/decode.h>
|
||||
#if defined(__GNUC__)
|
||||
#pragma GCC diagnostic pop
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_ZSTD
|
||||
#include <zstd.h>
|
||||
#endif
|
||||
|
||||
#include "sendf.h"
|
||||
|
@ -80,12 +90,13 @@ typedef enum {
|
|||
ZLIB_INIT_GZIP /* initialized in transparent gzip mode */
|
||||
} zlibInitState;
|
||||
|
||||
/* Writer parameters. */
|
||||
typedef struct {
|
||||
/* Deflate and gzip writer. */
|
||||
struct zlib_writer {
|
||||
struct contenc_writer super;
|
||||
zlibInitState zlib_init; /* zlib init state */
|
||||
uInt trailerlen; /* Remaining trailer byte count. */
|
||||
z_stream z; /* State structure for zlib. */
|
||||
} zlib_params;
|
||||
};
|
||||
|
||||
|
||||
static voidpf
|
||||
|
@ -104,9 +115,8 @@ zfree_cb(voidpf opaque, voidpf ptr)
|
|||
}
|
||||
|
||||
static CURLcode
|
||||
process_zlib_error(struct connectdata *conn, z_stream *z)
|
||||
process_zlib_error(struct Curl_easy *data, z_stream *z)
|
||||
{
|
||||
struct Curl_easy *data = conn->data;
|
||||
if(z->msg)
|
||||
failf(data, "Error while processing content unencoding: %s",
|
||||
z->msg);
|
||||
|
@ -118,7 +128,7 @@ process_zlib_error(struct connectdata *conn, z_stream *z)
|
|||
}
|
||||
|
||||
static CURLcode
|
||||
exit_zlib(struct connectdata *conn,
|
||||
exit_zlib(struct Curl_easy *data,
|
||||
z_stream *z, zlibInitState *zlib_init, CURLcode result)
|
||||
{
|
||||
if(*zlib_init == ZLIB_GZIP_HEADER)
|
||||
|
@ -126,14 +136,15 @@ exit_zlib(struct connectdata *conn,
|
|||
|
||||
if(*zlib_init != ZLIB_UNINIT) {
|
||||
if(inflateEnd(z) != Z_OK && result == CURLE_OK)
|
||||
result = process_zlib_error(conn, z);
|
||||
result = process_zlib_error(data, z);
|
||||
*zlib_init = ZLIB_UNINIT;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static CURLcode process_trailer(struct connectdata *conn, zlib_params *zp)
|
||||
static CURLcode process_trailer(struct Curl_easy *data,
|
||||
struct zlib_writer *zp)
|
||||
{
|
||||
z_stream *z = &zp->z;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
@ -148,7 +159,7 @@ static CURLcode process_trailer(struct connectdata *conn, zlib_params *zp)
|
|||
if(z->avail_in)
|
||||
result = CURLE_WRITE_ERROR;
|
||||
if(result || !zp->trailerlen)
|
||||
result = exit_zlib(conn, z, &zp->zlib_init, result);
|
||||
result = exit_zlib(data, z, &zp->zlib_init, result);
|
||||
else {
|
||||
/* Only occurs for gzip with zlib < 1.2.0.4 or raw deflate. */
|
||||
zp->zlib_init = ZLIB_EXTERNAL_TRAILER;
|
||||
|
@ -156,10 +167,11 @@ static CURLcode process_trailer(struct connectdata *conn, zlib_params *zp)
|
|||
return result;
|
||||
}
|
||||
|
||||
static CURLcode inflate_stream(struct connectdata *conn,
|
||||
contenc_writer *writer, zlibInitState started)
|
||||
static CURLcode inflate_stream(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
zlibInitState started)
|
||||
{
|
||||
zlib_params *zp = (zlib_params *) &writer->params;
|
||||
struct zlib_writer *zp = (struct zlib_writer *) writer;
|
||||
z_stream *z = &zp->z; /* zlib state structure */
|
||||
uInt nread = z->avail_in;
|
||||
Bytef *orig_in = z->next_in;
|
||||
|
@ -172,13 +184,13 @@ static CURLcode inflate_stream(struct connectdata *conn,
|
|||
zp->zlib_init != ZLIB_INFLATING &&
|
||||
zp->zlib_init != ZLIB_INIT_GZIP &&
|
||||
zp->zlib_init != ZLIB_GZIP_INFLATING)
|
||||
return exit_zlib(conn, z, &zp->zlib_init, CURLE_WRITE_ERROR);
|
||||
return exit_zlib(data, z, &zp->zlib_init, CURLE_WRITE_ERROR);
|
||||
|
||||
/* Dynamically allocate a buffer for decompression because it's uncommonly
|
||||
large to hold on the stack */
|
||||
decomp = malloc(DSIZ);
|
||||
if(decomp == NULL)
|
||||
return exit_zlib(conn, z, &zp->zlib_init, CURLE_OUT_OF_MEMORY);
|
||||
if(!decomp)
|
||||
return exit_zlib(data, z, &zp->zlib_init, CURLE_OUT_OF_MEMORY);
|
||||
|
||||
/* because the buffer size is fixed, iteratively decompress and transfer to
|
||||
the client via downstream_write function. */
|
||||
|
@ -202,10 +214,10 @@ static CURLcode inflate_stream(struct connectdata *conn,
|
|||
if(z->avail_out != DSIZ) {
|
||||
if(status == Z_OK || status == Z_STREAM_END) {
|
||||
zp->zlib_init = started; /* Data started. */
|
||||
result = Curl_unencode_write(conn, writer->downstream, decomp,
|
||||
result = Curl_unencode_write(data, writer->downstream, decomp,
|
||||
DSIZ - z->avail_out);
|
||||
if(result) {
|
||||
exit_zlib(conn, z, &zp->zlib_init, result);
|
||||
exit_zlib(data, z, &zp->zlib_init, result);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -221,7 +233,7 @@ static CURLcode inflate_stream(struct connectdata *conn,
|
|||
/* No more data to flush: just exit loop. */
|
||||
break;
|
||||
case Z_STREAM_END:
|
||||
result = process_trailer(conn, zp);
|
||||
result = process_trailer(data, zp);
|
||||
break;
|
||||
case Z_DATA_ERROR:
|
||||
/* some servers seem to not generate zlib headers, so this is an attempt
|
||||
|
@ -239,9 +251,10 @@ static CURLcode inflate_stream(struct connectdata *conn,
|
|||
}
|
||||
zp->zlib_init = ZLIB_UNINIT; /* inflateEnd() already called. */
|
||||
}
|
||||
/* FALLTHROUGH */
|
||||
result = exit_zlib(data, z, &zp->zlib_init, process_zlib_error(data, z));
|
||||
break;
|
||||
default:
|
||||
result = exit_zlib(conn, z, &zp->zlib_init, process_zlib_error(conn, z));
|
||||
result = exit_zlib(data, z, &zp->zlib_init, process_zlib_error(data, z));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -258,10 +271,10 @@ static CURLcode inflate_stream(struct connectdata *conn,
|
|||
|
||||
|
||||
/* Deflate handler. */
|
||||
static CURLcode deflate_init_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static CURLcode deflate_init_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
zlib_params *zp = (zlib_params *) &writer->params;
|
||||
struct zlib_writer *zp = (struct zlib_writer *) writer;
|
||||
z_stream *z = &zp->z; /* zlib state structure */
|
||||
|
||||
if(!writer->downstream)
|
||||
|
@ -272,16 +285,16 @@ static CURLcode deflate_init_writer(struct connectdata *conn,
|
|||
z->zfree = (free_func) zfree_cb;
|
||||
|
||||
if(inflateInit(z) != Z_OK)
|
||||
return process_zlib_error(conn, z);
|
||||
return process_zlib_error(data, z);
|
||||
zp->zlib_init = ZLIB_INIT;
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
static CURLcode deflate_unencode_write(struct connectdata *conn,
|
||||
contenc_writer *writer,
|
||||
static CURLcode deflate_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
zlib_params *zp = (zlib_params *) &writer->params;
|
||||
struct zlib_writer *zp = (struct zlib_writer *) writer;
|
||||
z_stream *z = &zp->z; /* zlib state structure */
|
||||
|
||||
/* Set the compressed input when this function is called */
|
||||
|
@ -289,36 +302,36 @@ static CURLcode deflate_unencode_write(struct connectdata *conn,
|
|||
z->avail_in = (uInt) nbytes;
|
||||
|
||||
if(zp->zlib_init == ZLIB_EXTERNAL_TRAILER)
|
||||
return process_trailer(conn, zp);
|
||||
return process_trailer(data, zp);
|
||||
|
||||
/* Now uncompress the data */
|
||||
return inflate_stream(conn, writer, ZLIB_INFLATING);
|
||||
return inflate_stream(data, writer, ZLIB_INFLATING);
|
||||
}
|
||||
|
||||
static void deflate_close_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static void deflate_close_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
zlib_params *zp = (zlib_params *) &writer->params;
|
||||
struct zlib_writer *zp = (struct zlib_writer *) writer;
|
||||
z_stream *z = &zp->z; /* zlib state structure */
|
||||
|
||||
exit_zlib(conn, z, &zp->zlib_init, CURLE_OK);
|
||||
exit_zlib(data, z, &zp->zlib_init, CURLE_OK);
|
||||
}
|
||||
|
||||
static const content_encoding deflate_encoding = {
|
||||
static const struct content_encoding deflate_encoding = {
|
||||
"deflate",
|
||||
NULL,
|
||||
deflate_init_writer,
|
||||
deflate_unencode_write,
|
||||
deflate_close_writer,
|
||||
sizeof(zlib_params)
|
||||
sizeof(struct zlib_writer)
|
||||
};
|
||||
|
||||
|
||||
/* Gzip handler. */
|
||||
static CURLcode gzip_init_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static CURLcode gzip_init_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
zlib_params *zp = (zlib_params *) &writer->params;
|
||||
struct zlib_writer *zp = (struct zlib_writer *) writer;
|
||||
z_stream *z = &zp->z; /* zlib state structure */
|
||||
|
||||
if(!writer->downstream)
|
||||
|
@ -331,14 +344,14 @@ static CURLcode gzip_init_writer(struct connectdata *conn,
|
|||
if(strcmp(zlibVersion(), "1.2.0.4") >= 0) {
|
||||
/* zlib ver. >= 1.2.0.4 supports transparent gzip decompressing */
|
||||
if(inflateInit2(z, MAX_WBITS + 32) != Z_OK) {
|
||||
return process_zlib_error(conn, z);
|
||||
return process_zlib_error(data, z);
|
||||
}
|
||||
zp->zlib_init = ZLIB_INIT_GZIP; /* Transparent gzip decompress state */
|
||||
}
|
||||
else {
|
||||
/* we must parse the gzip header and trailer ourselves */
|
||||
if(inflateInit2(z, -MAX_WBITS) != Z_OK) {
|
||||
return process_zlib_error(conn, z);
|
||||
return process_zlib_error(data, z);
|
||||
}
|
||||
zp->trailerlen = 8; /* A CRC-32 and a 32-bit input size (RFC 1952, 2.2) */
|
||||
zp->zlib_init = ZLIB_INIT; /* Initial call state */
|
||||
|
@ -431,11 +444,11 @@ static enum {
|
|||
}
|
||||
#endif
|
||||
|
||||
static CURLcode gzip_unencode_write(struct connectdata *conn,
|
||||
contenc_writer *writer,
|
||||
static CURLcode gzip_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
zlib_params *zp = (zlib_params *) &writer->params;
|
||||
struct zlib_writer *zp = (struct zlib_writer *) writer;
|
||||
z_stream *z = &zp->z; /* zlib state structure */
|
||||
|
||||
if(zp->zlib_init == ZLIB_INIT_GZIP) {
|
||||
|
@ -443,13 +456,13 @@ static CURLcode gzip_unencode_write(struct connectdata *conn,
|
|||
z->next_in = (Bytef *) buf;
|
||||
z->avail_in = (uInt) nbytes;
|
||||
/* Now uncompress the data */
|
||||
return inflate_stream(conn, writer, ZLIB_INIT_GZIP);
|
||||
return inflate_stream(data, writer, ZLIB_INIT_GZIP);
|
||||
}
|
||||
|
||||
#ifndef OLD_ZLIB_SUPPORT
|
||||
/* Support for old zlib versions is compiled away and we are running with
|
||||
an old version, so return an error. */
|
||||
return exit_zlib(conn, z, &zp->zlib_init, CURLE_WRITE_ERROR);
|
||||
return exit_zlib(data, z, &zp->zlib_init, CURLE_WRITE_ERROR);
|
||||
|
||||
#else
|
||||
/* This next mess is to get around the potential case where there isn't
|
||||
|
@ -486,8 +499,8 @@ static CURLcode gzip_unencode_write(struct connectdata *conn,
|
|||
*/
|
||||
z->avail_in = (uInt) nbytes;
|
||||
z->next_in = malloc(z->avail_in);
|
||||
if(z->next_in == NULL) {
|
||||
return exit_zlib(conn, z, &zp->zlib_init, CURLE_OUT_OF_MEMORY);
|
||||
if(!z->next_in) {
|
||||
return exit_zlib(data, z, &zp->zlib_init, CURLE_OUT_OF_MEMORY);
|
||||
}
|
||||
memcpy(z->next_in, buf, z->avail_in);
|
||||
zp->zlib_init = ZLIB_GZIP_HEADER; /* Need more gzip header data state */
|
||||
|
@ -496,7 +509,7 @@ static CURLcode gzip_unencode_write(struct connectdata *conn,
|
|||
|
||||
case GZIP_BAD:
|
||||
default:
|
||||
return exit_zlib(conn, z, &zp->zlib_init, process_zlib_error(conn, z));
|
||||
return exit_zlib(data, z, &zp->zlib_init, process_zlib_error(data, z));
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -508,8 +521,8 @@ static CURLcode gzip_unencode_write(struct connectdata *conn,
|
|||
ssize_t hlen;
|
||||
z->avail_in += (uInt) nbytes;
|
||||
z->next_in = Curl_saferealloc(z->next_in, z->avail_in);
|
||||
if(z->next_in == NULL) {
|
||||
return exit_zlib(conn, z, &zp->zlib_init, CURLE_OUT_OF_MEMORY);
|
||||
if(!z->next_in) {
|
||||
return exit_zlib(data, z, &zp->zlib_init, CURLE_OUT_OF_MEMORY);
|
||||
}
|
||||
/* Append the new block of data to the previous one */
|
||||
memcpy(z->next_in + z->avail_in - nbytes, buf, nbytes);
|
||||
|
@ -530,7 +543,7 @@ static CURLcode gzip_unencode_write(struct connectdata *conn,
|
|||
|
||||
case GZIP_BAD:
|
||||
default:
|
||||
return exit_zlib(conn, z, &zp->zlib_init, process_zlib_error(conn, z));
|
||||
return exit_zlib(data, z, &zp->zlib_init, process_zlib_error(data, z));
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -539,7 +552,7 @@ static CURLcode gzip_unencode_write(struct connectdata *conn,
|
|||
case ZLIB_EXTERNAL_TRAILER:
|
||||
z->next_in = (Bytef *) buf;
|
||||
z->avail_in = (uInt) nbytes;
|
||||
return process_trailer(conn, zp);
|
||||
return process_trailer(data, zp);
|
||||
|
||||
case ZLIB_GZIP_INFLATING:
|
||||
default:
|
||||
|
@ -555,38 +568,37 @@ static CURLcode gzip_unencode_write(struct connectdata *conn,
|
|||
}
|
||||
|
||||
/* We've parsed the header, now uncompress the data */
|
||||
return inflate_stream(conn, writer, ZLIB_GZIP_INFLATING);
|
||||
return inflate_stream(data, writer, ZLIB_GZIP_INFLATING);
|
||||
#endif
|
||||
}
|
||||
|
||||
static void gzip_close_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static void gzip_close_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
zlib_params *zp = (zlib_params *) &writer->params;
|
||||
struct zlib_writer *zp = (struct zlib_writer *) writer;
|
||||
z_stream *z = &zp->z; /* zlib state structure */
|
||||
|
||||
exit_zlib(conn, z, &zp->zlib_init, CURLE_OK);
|
||||
exit_zlib(data, z, &zp->zlib_init, CURLE_OK);
|
||||
}
|
||||
|
||||
static const content_encoding gzip_encoding = {
|
||||
static const struct content_encoding gzip_encoding = {
|
||||
"gzip",
|
||||
"x-gzip",
|
||||
gzip_init_writer,
|
||||
gzip_unencode_write,
|
||||
gzip_close_writer,
|
||||
sizeof(zlib_params)
|
||||
sizeof(struct zlib_writer)
|
||||
};
|
||||
|
||||
#endif /* HAVE_LIBZ */
|
||||
|
||||
|
||||
#ifdef HAVE_BROTLI
|
||||
|
||||
/* Writer parameters. */
|
||||
typedef struct {
|
||||
/* Brotli writer. */
|
||||
struct brotli_writer {
|
||||
struct contenc_writer super;
|
||||
BrotliDecoderState *br; /* State structure for brotli. */
|
||||
} brotli_params;
|
||||
|
||||
};
|
||||
|
||||
static CURLcode brotli_map_error(BrotliDecoderErrorCode be)
|
||||
{
|
||||
|
@ -626,12 +638,11 @@ static CURLcode brotli_map_error(BrotliDecoderErrorCode be)
|
|||
return CURLE_WRITE_ERROR;
|
||||
}
|
||||
|
||||
static CURLcode brotli_init_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static CURLcode brotli_init_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
brotli_params *bp = (brotli_params *) &writer->params;
|
||||
|
||||
(void) conn;
|
||||
struct brotli_writer *bp = (struct brotli_writer *) writer;
|
||||
(void) data;
|
||||
|
||||
if(!writer->downstream)
|
||||
return CURLE_WRITE_ERROR;
|
||||
|
@ -640,11 +651,11 @@ static CURLcode brotli_init_writer(struct connectdata *conn,
|
|||
return bp->br? CURLE_OK: CURLE_OUT_OF_MEMORY;
|
||||
}
|
||||
|
||||
static CURLcode brotli_unencode_write(struct connectdata *conn,
|
||||
contenc_writer *writer,
|
||||
static CURLcode brotli_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
brotli_params *bp = (brotli_params *) &writer->params;
|
||||
struct brotli_writer *bp = (struct brotli_writer *) writer;
|
||||
const uint8_t *src = (const uint8_t *) buf;
|
||||
char *decomp;
|
||||
uint8_t *dst;
|
||||
|
@ -665,7 +676,7 @@ static CURLcode brotli_unencode_write(struct connectdata *conn,
|
|||
dstleft = DSIZ;
|
||||
r = BrotliDecoderDecompressStream(bp->br,
|
||||
&nbytes, &src, &dstleft, &dst, NULL);
|
||||
result = Curl_unencode_write(conn, writer->downstream,
|
||||
result = Curl_unencode_write(data, writer->downstream,
|
||||
decomp, DSIZ - dstleft);
|
||||
if(result)
|
||||
break;
|
||||
|
@ -688,12 +699,12 @@ static CURLcode brotli_unencode_write(struct connectdata *conn,
|
|||
return result;
|
||||
}
|
||||
|
||||
static void brotli_close_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static void brotli_close_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
brotli_params *bp = (brotli_params *) &writer->params;
|
||||
struct brotli_writer *bp = (struct brotli_writer *) writer;
|
||||
|
||||
(void) conn;
|
||||
(void) data;
|
||||
|
||||
if(bp->br) {
|
||||
BrotliDecoderDestroyInstance(bp->br);
|
||||
|
@ -701,51 +712,143 @@ static void brotli_close_writer(struct connectdata *conn,
|
|||
}
|
||||
}
|
||||
|
||||
static const content_encoding brotli_encoding = {
|
||||
static const struct content_encoding brotli_encoding = {
|
||||
"br",
|
||||
NULL,
|
||||
brotli_init_writer,
|
||||
brotli_unencode_write,
|
||||
brotli_close_writer,
|
||||
sizeof(brotli_params)
|
||||
sizeof(struct brotli_writer)
|
||||
};
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef HAVE_ZSTD
|
||||
/* Zstd writer. */
|
||||
struct zstd_writer {
|
||||
struct contenc_writer super;
|
||||
ZSTD_DStream *zds; /* State structure for zstd. */
|
||||
void *decomp;
|
||||
};
|
||||
|
||||
static CURLcode zstd_init_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
struct zstd_writer *zp = (struct zstd_writer *) writer;
|
||||
|
||||
(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;
|
||||
}
|
||||
|
||||
static CURLcode zstd_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
CURLcode result = CURLE_OK;
|
||||
struct zstd_writer *zp = (struct zstd_writer *) writer;
|
||||
ZSTD_inBuffer in;
|
||||
ZSTD_outBuffer out;
|
||||
size_t errorCode;
|
||||
|
||||
if(!zp->decomp) {
|
||||
zp->decomp = malloc(DSIZ);
|
||||
if(!zp->decomp)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
}
|
||||
in.pos = 0;
|
||||
in.src = buf;
|
||||
in.size = nbytes;
|
||||
|
||||
for(;;) {
|
||||
out.pos = 0;
|
||||
out.dst = zp->decomp;
|
||||
out.size = DSIZ;
|
||||
|
||||
errorCode = ZSTD_decompressStream(zp->zds, &out, &in);
|
||||
if(ZSTD_isError(errorCode)) {
|
||||
return CURLE_BAD_CONTENT_ENCODING;
|
||||
}
|
||||
if(out.pos > 0) {
|
||||
result = Curl_unencode_write(data, writer->downstream,
|
||||
zp->decomp, out.pos);
|
||||
if(result)
|
||||
break;
|
||||
}
|
||||
if((in.pos == nbytes) && (out.pos < out.size))
|
||||
break;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static void zstd_close_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
struct zstd_writer *zp = (struct zstd_writer *) writer;
|
||||
|
||||
(void)data;
|
||||
|
||||
if(zp->decomp) {
|
||||
free(zp->decomp);
|
||||
zp->decomp = NULL;
|
||||
}
|
||||
if(zp->zds) {
|
||||
ZSTD_freeDStream(zp->zds);
|
||||
zp->zds = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static const struct content_encoding zstd_encoding = {
|
||||
"zstd",
|
||||
NULL,
|
||||
zstd_init_writer,
|
||||
zstd_unencode_write,
|
||||
zstd_close_writer,
|
||||
sizeof(struct zstd_writer)
|
||||
};
|
||||
#endif
|
||||
|
||||
|
||||
/* Identity handler. */
|
||||
static CURLcode identity_init_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static CURLcode identity_init_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
return writer->downstream? CURLE_OK: CURLE_WRITE_ERROR;
|
||||
}
|
||||
|
||||
static CURLcode identity_unencode_write(struct connectdata *conn,
|
||||
contenc_writer *writer,
|
||||
static CURLcode identity_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
return Curl_unencode_write(conn, writer->downstream, buf, nbytes);
|
||||
return Curl_unencode_write(data, writer->downstream, buf, nbytes);
|
||||
}
|
||||
|
||||
static void identity_close_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static void identity_close_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
(void) writer;
|
||||
}
|
||||
|
||||
static const content_encoding identity_encoding = {
|
||||
static const struct content_encoding identity_encoding = {
|
||||
"identity",
|
||||
"none",
|
||||
identity_init_writer,
|
||||
identity_unencode_write,
|
||||
identity_close_writer,
|
||||
0
|
||||
sizeof(struct contenc_writer)
|
||||
};
|
||||
|
||||
|
||||
/* supported content encodings table. */
|
||||
static const content_encoding * const encodings[] = {
|
||||
static const struct content_encoding * const encodings[] = {
|
||||
&identity_encoding,
|
||||
#ifdef HAVE_LIBZ
|
||||
&deflate_encoding,
|
||||
|
@ -753,6 +856,9 @@ static const content_encoding * const encodings[] = {
|
|||
#endif
|
||||
#ifdef HAVE_BROTLI
|
||||
&brotli_encoding,
|
||||
#endif
|
||||
#ifdef HAVE_ZSTD
|
||||
&zstd_encoding,
|
||||
#endif
|
||||
NULL
|
||||
};
|
||||
|
@ -762,8 +868,8 @@ static const content_encoding * const encodings[] = {
|
|||
char *Curl_all_content_encodings(void)
|
||||
{
|
||||
size_t len = 0;
|
||||
const content_encoding * const *cep;
|
||||
const content_encoding *ce;
|
||||
const struct content_encoding * const *cep;
|
||||
const struct content_encoding *ce;
|
||||
char *ace;
|
||||
|
||||
for(cep = encodings; *cep; cep++) {
|
||||
|
@ -795,18 +901,17 @@ char *Curl_all_content_encodings(void)
|
|||
|
||||
|
||||
/* Real client writer: no downstream. */
|
||||
static CURLcode client_init_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static CURLcode client_init_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
return writer->downstream? CURLE_WRITE_ERROR: CURLE_OK;
|
||||
}
|
||||
|
||||
static CURLcode client_unencode_write(struct connectdata *conn,
|
||||
contenc_writer *writer,
|
||||
static CURLcode client_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct SingleRequest *k = &data->req;
|
||||
|
||||
(void) writer;
|
||||
|
@ -814,36 +919,36 @@ static CURLcode client_unencode_write(struct connectdata *conn,
|
|||
if(!nbytes || k->ignorebody)
|
||||
return CURLE_OK;
|
||||
|
||||
return Curl_client_write(conn, CLIENTWRITE_BODY, (char *) buf, nbytes);
|
||||
return Curl_client_write(data, CLIENTWRITE_BODY, (char *) buf, nbytes);
|
||||
}
|
||||
|
||||
static void client_close_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static void client_close_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
(void) writer;
|
||||
}
|
||||
|
||||
static const content_encoding client_encoding = {
|
||||
static const struct content_encoding client_encoding = {
|
||||
NULL,
|
||||
NULL,
|
||||
client_init_writer,
|
||||
client_unencode_write,
|
||||
client_close_writer,
|
||||
0
|
||||
sizeof(struct contenc_writer)
|
||||
};
|
||||
|
||||
|
||||
/* Deferred error dummy writer. */
|
||||
static CURLcode error_init_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static CURLcode error_init_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
return writer->downstream? CURLE_OK: CURLE_WRITE_ERROR;
|
||||
}
|
||||
|
||||
static CURLcode error_unencode_write(struct connectdata *conn,
|
||||
contenc_writer *writer,
|
||||
static CURLcode error_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
char *all = Curl_all_content_encodings();
|
||||
|
@ -854,40 +959,45 @@ static CURLcode error_unencode_write(struct connectdata *conn,
|
|||
|
||||
if(!all)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
failf(conn->data, "Unrecognized content encoding type. "
|
||||
"libcurl understands %s content encodings.", all);
|
||||
failf(data, "Unrecognized content encoding type. "
|
||||
"libcurl understands %s content encodings.", all);
|
||||
free(all);
|
||||
return CURLE_BAD_CONTENT_ENCODING;
|
||||
}
|
||||
|
||||
static void error_close_writer(struct connectdata *conn,
|
||||
contenc_writer *writer)
|
||||
static void error_close_writer(struct Curl_easy *data,
|
||||
struct contenc_writer *writer)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
(void) writer;
|
||||
}
|
||||
|
||||
static const content_encoding error_encoding = {
|
||||
static const struct content_encoding error_encoding = {
|
||||
NULL,
|
||||
NULL,
|
||||
error_init_writer,
|
||||
error_unencode_write,
|
||||
error_close_writer,
|
||||
0
|
||||
sizeof(struct contenc_writer)
|
||||
};
|
||||
|
||||
/* Create an unencoding writer stage using the given handler. */
|
||||
static contenc_writer *new_unencoding_writer(struct connectdata *conn,
|
||||
const content_encoding *handler,
|
||||
contenc_writer *downstream)
|
||||
static struct contenc_writer *
|
||||
new_unencoding_writer(struct Curl_easy *data,
|
||||
const struct content_encoding *handler,
|
||||
struct contenc_writer *downstream,
|
||||
int order)
|
||||
{
|
||||
size_t sz = offsetof(contenc_writer, params) + handler->paramsize;
|
||||
contenc_writer *writer = (contenc_writer *) calloc(1, sz);
|
||||
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;
|
||||
if(handler->init_writer(conn, writer)) {
|
||||
writer->order = order;
|
||||
if(handler->init_writer(data, writer)) {
|
||||
free(writer);
|
||||
writer = NULL;
|
||||
}
|
||||
|
@ -896,37 +1006,39 @@ static contenc_writer *new_unencoding_writer(struct connectdata *conn,
|
|||
return writer;
|
||||
}
|
||||
|
||||
/* Write data using an unencoding writer stack. */
|
||||
CURLcode Curl_unencode_write(struct connectdata *conn, contenc_writer *writer,
|
||||
/* Write data using an unencoding writer stack. "nbytes" is not
|
||||
allowed to be 0. */
|
||||
CURLcode Curl_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
if(!nbytes)
|
||||
return CURLE_OK;
|
||||
return writer->handler->unencode_write(conn, writer, buf, nbytes);
|
||||
return writer->handler->unencode_write(data, writer, buf, nbytes);
|
||||
}
|
||||
|
||||
/* Close and clean-up the connection's writer stack. */
|
||||
void Curl_unencode_cleanup(struct connectdata *conn)
|
||||
void Curl_unencode_cleanup(struct Curl_easy *data)
|
||||
{
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct SingleRequest *k = &data->req;
|
||||
contenc_writer *writer = k->writer_stack;
|
||||
struct contenc_writer *writer = k->writer_stack;
|
||||
|
||||
while(writer) {
|
||||
k->writer_stack = writer->downstream;
|
||||
writer->handler->close_writer(conn, writer);
|
||||
writer->handler->close_writer(data, writer);
|
||||
free(writer);
|
||||
writer = k->writer_stack;
|
||||
}
|
||||
}
|
||||
|
||||
/* Find the content encoding by name. */
|
||||
static const content_encoding *find_encoding(const char *name, size_t len)
|
||||
static const struct content_encoding *find_encoding(const char *name,
|
||||
size_t len)
|
||||
{
|
||||
const content_encoding * const *cep;
|
||||
const struct content_encoding * const *cep;
|
||||
|
||||
for(cep = encodings; *cep; cep++) {
|
||||
const content_encoding *ce = *cep;
|
||||
const struct content_encoding *ce = *cep;
|
||||
if((strncasecompare(name, ce->name, len) && !ce->name[len]) ||
|
||||
(ce->alias && strncasecompare(name, ce->alias, len) && !ce->alias[len]))
|
||||
return ce;
|
||||
|
@ -934,20 +1046,23 @@ static const content_encoding *find_encoding(const char *name, size_t len)
|
|||
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 connectdata *conn,
|
||||
const char *enclist, int maybechunked)
|
||||
CURLcode Curl_build_unencoding_stack(struct Curl_easy *data,
|
||||
const char *enclist, int is_transfer)
|
||||
{
|
||||
struct Curl_easy *data = conn->data;
|
||||
struct SingleRequest *k = &data->req;
|
||||
unsigned int order = is_transfer? 2: 1;
|
||||
|
||||
do {
|
||||
const char *name;
|
||||
size_t namelen;
|
||||
|
||||
/* Parse a single encoding name. */
|
||||
while(ISSPACE(*enclist) || *enclist == ',')
|
||||
while(ISBLANK(*enclist) || *enclist == ',')
|
||||
enclist++;
|
||||
|
||||
name = enclist;
|
||||
|
@ -957,16 +1072,17 @@ CURLcode Curl_build_unencoding_stack(struct connectdata *conn,
|
|||
namelen = enclist - name + 1;
|
||||
|
||||
/* Special case: chunked encoding is handled at the reader level. */
|
||||
if(maybechunked && namelen == 7 && strncasecompare(name, "chunked", 7)) {
|
||||
if(is_transfer && namelen == 7 && strncasecompare(name, "chunked", 7)) {
|
||||
k->chunk = TRUE; /* chunks coming our way. */
|
||||
Curl_httpchunk_init(conn); /* init our chunky engine. */
|
||||
Curl_httpchunk_init(data); /* init our chunky engine. */
|
||||
}
|
||||
else if(namelen) {
|
||||
const content_encoding *encoding = find_encoding(name, namelen);
|
||||
contenc_writer *writer;
|
||||
const struct content_encoding *encoding = find_encoding(name, namelen);
|
||||
struct contenc_writer *writer;
|
||||
|
||||
if(!k->writer_stack) {
|
||||
k->writer_stack = new_unencoding_writer(conn, &client_encoding, NULL);
|
||||
k->writer_stack = new_unencoding_writer(data, &client_encoding,
|
||||
NULL, 0);
|
||||
|
||||
if(!k->writer_stack)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
@ -975,11 +1091,29 @@ CURLcode Curl_build_unencoding_stack(struct connectdata *conn,
|
|||
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. */
|
||||
writer = new_unencoding_writer(conn, encoding, k->writer_stack);
|
||||
if(!writer)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
k->writer_stack = writer;
|
||||
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;
|
||||
}
|
||||
}
|
||||
} while(*enclist);
|
||||
|
||||
|
@ -988,28 +1122,29 @@ CURLcode Curl_build_unencoding_stack(struct connectdata *conn,
|
|||
|
||||
#else
|
||||
/* Stubs for builds without HTTP. */
|
||||
CURLcode Curl_build_unencoding_stack(struct connectdata *conn,
|
||||
const char *enclist, int maybechunked)
|
||||
CURLcode Curl_build_unencoding_stack(struct Curl_easy *data,
|
||||
const char *enclist, int is_transfer)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
(void) enclist;
|
||||
(void) maybechunked;
|
||||
(void) is_transfer;
|
||||
return CURLE_NOT_BUILT_IN;
|
||||
}
|
||||
|
||||
CURLcode Curl_unencode_write(struct connectdata *conn, contenc_writer *writer,
|
||||
CURLcode Curl_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
(void) writer;
|
||||
(void) buf;
|
||||
(void) nbytes;
|
||||
return CURLE_NOT_BUILT_IN;
|
||||
}
|
||||
|
||||
void Curl_unencode_cleanup(struct connectdata *conn)
|
||||
void Curl_unencode_cleanup(struct Curl_easy *data)
|
||||
{
|
||||
(void) conn;
|
||||
(void) data;
|
||||
}
|
||||
|
||||
char *Curl_all_content_encodings(void)
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2017, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,36 +20,38 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
/* Decoding writer. */
|
||||
typedef struct contenc_writer_s contenc_writer;
|
||||
typedef struct content_encoding_s content_encoding;
|
||||
|
||||
struct contenc_writer_s {
|
||||
const content_encoding *handler; /* Encoding handler. */
|
||||
contenc_writer *downstream; /* Downstream writer. */
|
||||
void *params; /* Encoding-specific storage (variable length). */
|
||||
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_s {
|
||||
struct content_encoding {
|
||||
const char *name; /* Encoding name. */
|
||||
const char *alias; /* Encoding name alias. */
|
||||
CURLcode (*init_writer)(struct connectdata *conn, contenc_writer *writer);
|
||||
CURLcode (*unencode_write)(struct connectdata *conn, contenc_writer *writer,
|
||||
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 connectdata *conn, contenc_writer *writer);
|
||||
size_t paramsize;
|
||||
void (*close_writer)(struct Curl_easy *data,
|
||||
struct contenc_writer *writer);
|
||||
size_t writersize;
|
||||
};
|
||||
|
||||
|
||||
CURLcode Curl_build_unencoding_stack(struct connectdata *conn,
|
||||
const char *enclist, int maybechunked);
|
||||
CURLcode Curl_unencode_write(struct connectdata *conn, contenc_writer *writer,
|
||||
CURLcode Curl_build_unencoding_stack(struct Curl_easy *data,
|
||||
const char *enclist, int is_transfer);
|
||||
CURLcode Curl_unencode_write(struct Curl_easy *data,
|
||||
struct contenc_writer *writer,
|
||||
const char *buf, size_t nbytes);
|
||||
void Curl_unencode_cleanup(struct connectdata *conn);
|
||||
void Curl_unencode_cleanup(struct Curl_easy *data);
|
||||
char *Curl_all_content_encodings(void);
|
||||
|
||||
#endif /* HEADER_CURL_CONTENT_ENCODING_H */
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
|
@ -34,12 +36,12 @@ struct Cookie {
|
|||
char *domain; /* domain = <this> */
|
||||
curl_off_t expires; /* expires = <this> */
|
||||
char *expirestr; /* the plain text version */
|
||||
bool tailmatch; /* whether we do tail-matching of the domain name */
|
||||
|
||||
/* 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 */
|
||||
bool httponly; /* true if the httponly directive is present */
|
||||
|
@ -61,10 +63,11 @@ struct CookieInfo {
|
|||
struct Cookie *cookies[COOKIE_HASH_SIZE];
|
||||
|
||||
char *filename; /* file we read from/write to */
|
||||
bool running; /* state info, for cookie adding information */
|
||||
long numcookies; /* number of cookies 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 */
|
||||
};
|
||||
|
||||
/* This is the maximum line length we accept for a cookie line. RFC 2109
|
||||
|
@ -80,10 +83,26 @@ struct CookieInfo {
|
|||
*/
|
||||
#define MAX_COOKIE_LINE 5000
|
||||
|
||||
/* This is the maximum length of a cookie name or content we deal with: */
|
||||
/* Maximum length of an incoming cookie name or content we deal with. Longer
|
||||
cookies are ignored. */
|
||||
#define MAX_NAME 4096
|
||||
#define MAX_NAME_TXT "4095"
|
||||
|
||||
/* Maximum size for an outgoing cookie line libcurl will use in an http
|
||||
request. This is the default maximum length used in some versions of Apache
|
||||
httpd. */
|
||||
#define MAX_COOKIE_HEADER_LEN 8190
|
||||
|
||||
/* Maximum number of cookies libcurl will send in a single request, even if
|
||||
there might be more cookies that match. One reason to cap the number is to
|
||||
keep the maximum HTTP request within the maximum allowed size. */
|
||||
#define MAX_COOKIE_SEND_AMOUNT 150
|
||||
|
||||
/* Maximum number of Set-Cookie: lines accepted in a single response. If more
|
||||
such header lines are received, they are ignored. This value must be less
|
||||
than 256 since an unsigned char is used to count. */
|
||||
#define MAX_SET_COOKIE_AMOUNT 50
|
||||
|
||||
struct Curl_easy;
|
||||
/*
|
||||
* Add a cookie to the internal list of cookies. The domain and path arguments
|
||||
|
@ -91,13 +110,14 @@ struct Curl_easy;
|
|||
*/
|
||||
|
||||
struct Cookie *Curl_cookie_add(struct Curl_easy *data,
|
||||
struct CookieInfo *, bool header, bool noexpiry,
|
||||
char *lineptr,
|
||||
struct CookieInfo *c, bool header,
|
||||
bool noexpiry, char *lineptr,
|
||||
const char *domain, const char *path,
|
||||
bool secure);
|
||||
|
||||
struct Cookie *Curl_cookie_getlist(struct CookieInfo *, const char *,
|
||||
const char *, bool);
|
||||
struct Cookie *Curl_cookie_getlist(struct Curl_easy *data,
|
||||
struct CookieInfo *c, const char *host,
|
||||
const char *path, bool secure);
|
||||
void Curl_cookie_freelist(struct Cookie *cookies);
|
||||
void Curl_cookie_clearall(struct CookieInfo *cookies);
|
||||
void Curl_cookie_clearsess(struct CookieInfo *cookies);
|
||||
|
@ -109,10 +129,11 @@ void Curl_cookie_clearsess(struct CookieInfo *cookies);
|
|||
#define Curl_cookie_cleanup(x) Curl_nop_stmt
|
||||
#define Curl_flush_cookies(x,y) Curl_nop_stmt
|
||||
#else
|
||||
void Curl_flush_cookies(struct Curl_easy *data, int cleanup);
|
||||
void Curl_cookie_cleanup(struct CookieInfo *);
|
||||
void Curl_flush_cookies(struct Curl_easy *data, bool cleanup);
|
||||
void Curl_cookie_cleanup(struct CookieInfo *c);
|
||||
struct CookieInfo *Curl_cookie_init(struct Curl_easy *data,
|
||||
const char *, struct CookieInfo *, bool);
|
||||
const char *file, struct CookieInfo *inc,
|
||||
bool newsession);
|
||||
struct curl_slist *Curl_cookie_list(struct Curl_easy *data);
|
||||
void Curl_cookie_loadfiles(struct Curl_easy *data);
|
||||
#endif
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -45,15 +47,6 @@
|
|||
# include <inet.h>
|
||||
#endif
|
||||
|
||||
#if defined(NETWARE) && defined(__NOVELL_LIBC__)
|
||||
# undef in_addr_t
|
||||
# define in_addr_t unsigned long
|
||||
#endif
|
||||
|
||||
#if defined(WIN32) && defined(USE_UNIX_SOCKETS)
|
||||
#include <afunix.h>
|
||||
#endif
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
#include "curl_addrinfo.h"
|
||||
|
@ -82,16 +75,13 @@
|
|||
#endif
|
||||
|
||||
void
|
||||
Curl_freeaddrinfo(Curl_addrinfo *cahead)
|
||||
Curl_freeaddrinfo(struct Curl_addrinfo *cahead)
|
||||
{
|
||||
Curl_addrinfo *vqualifier canext;
|
||||
Curl_addrinfo *ca;
|
||||
struct Curl_addrinfo *vqualifier canext;
|
||||
struct Curl_addrinfo *ca;
|
||||
|
||||
for(ca = cahead; ca != NULL; ca = canext) {
|
||||
free(ca->ai_addr);
|
||||
free(ca->ai_canonname);
|
||||
for(ca = cahead; ca; ca = canext) {
|
||||
canext = ca->ai_next;
|
||||
|
||||
free(ca);
|
||||
}
|
||||
}
|
||||
|
@ -116,13 +106,13 @@ int
|
|||
Curl_getaddrinfo_ex(const char *nodename,
|
||||
const char *servname,
|
||||
const struct addrinfo *hints,
|
||||
Curl_addrinfo **result)
|
||||
struct Curl_addrinfo **result)
|
||||
{
|
||||
const struct addrinfo *ai;
|
||||
struct addrinfo *aihead;
|
||||
Curl_addrinfo *cafirst = NULL;
|
||||
Curl_addrinfo *calast = NULL;
|
||||
Curl_addrinfo *ca;
|
||||
struct Curl_addrinfo *cafirst = NULL;
|
||||
struct Curl_addrinfo *calast = NULL;
|
||||
struct Curl_addrinfo *ca;
|
||||
size_t ss_size;
|
||||
int error;
|
||||
|
||||
|
@ -135,7 +125,7 @@ Curl_getaddrinfo_ex(const char *nodename,
|
|||
/* traverse the addrinfo list */
|
||||
|
||||
for(ai = aihead; ai != NULL; ai = ai->ai_next) {
|
||||
|
||||
size_t namelen = ai->ai_canonname ? strlen(ai->ai_canonname) + 1 : 0;
|
||||
/* ignore elements with unsupported address family, */
|
||||
/* settle family-specific sockaddr structure size. */
|
||||
if(ai->ai_family == AF_INET)
|
||||
|
@ -148,14 +138,14 @@ Curl_getaddrinfo_ex(const char *nodename,
|
|||
continue;
|
||||
|
||||
/* ignore elements without required address info */
|
||||
if((ai->ai_addr == NULL) || !(ai->ai_addrlen > 0))
|
||||
if(!ai->ai_addr || !(ai->ai_addrlen > 0))
|
||||
continue;
|
||||
|
||||
/* ignore elements with bogus address size */
|
||||
if((size_t)ai->ai_addrlen < ss_size)
|
||||
continue;
|
||||
|
||||
ca = malloc(sizeof(Curl_addrinfo));
|
||||
ca = malloc(sizeof(struct Curl_addrinfo) + ss_size + namelen);
|
||||
if(!ca) {
|
||||
error = EAI_MEMORY;
|
||||
break;
|
||||
|
@ -173,22 +163,12 @@ Curl_getaddrinfo_ex(const char *nodename,
|
|||
ca->ai_canonname = NULL;
|
||||
ca->ai_next = NULL;
|
||||
|
||||
ca->ai_addr = malloc(ss_size);
|
||||
if(!ca->ai_addr) {
|
||||
error = EAI_MEMORY;
|
||||
free(ca);
|
||||
break;
|
||||
}
|
||||
ca->ai_addr = (void *)((char *)ca + sizeof(struct Curl_addrinfo));
|
||||
memcpy(ca->ai_addr, ai->ai_addr, ss_size);
|
||||
|
||||
if(ai->ai_canonname != NULL) {
|
||||
ca->ai_canonname = strdup(ai->ai_canonname);
|
||||
if(!ca->ai_canonname) {
|
||||
error = EAI_MEMORY;
|
||||
free(ca->ai_addr);
|
||||
free(ca);
|
||||
break;
|
||||
}
|
||||
if(namelen) {
|
||||
ca->ai_canonname = (void *)((char *)ca->ai_addr + ss_size);
|
||||
memcpy(ca->ai_canonname, ai->ai_canonname, namelen);
|
||||
}
|
||||
|
||||
/* if the return list is empty, this becomes the first element */
|
||||
|
@ -256,7 +236,6 @@ Curl_getaddrinfo_ex(const char *nodename,
|
|||
* struct sockaddr *ai_addr;
|
||||
* struct Curl_addrinfo *ai_next;
|
||||
* };
|
||||
* typedef struct Curl_addrinfo Curl_addrinfo;
|
||||
*
|
||||
* hostent defined in <netdb.h>
|
||||
*
|
||||
|
@ -273,12 +252,12 @@ Curl_getaddrinfo_ex(const char *nodename,
|
|||
* #define h_addr h_addr_list[0]
|
||||
*/
|
||||
|
||||
Curl_addrinfo *
|
||||
struct Curl_addrinfo *
|
||||
Curl_he2ai(const struct hostent *he, int port)
|
||||
{
|
||||
Curl_addrinfo *ai;
|
||||
Curl_addrinfo *prevai = NULL;
|
||||
Curl_addrinfo *firstai = NULL;
|
||||
struct Curl_addrinfo *ai;
|
||||
struct Curl_addrinfo *prevai = NULL;
|
||||
struct Curl_addrinfo *firstai = NULL;
|
||||
struct sockaddr_in *addr;
|
||||
#ifdef ENABLE_IPV6
|
||||
struct sockaddr_in6 *addr6;
|
||||
|
@ -294,8 +273,8 @@ Curl_he2ai(const struct hostent *he, int port)
|
|||
DEBUGASSERT((he->h_name != NULL) && (he->h_addr_list != NULL));
|
||||
|
||||
for(i = 0; (curr = he->h_addr_list[i]) != NULL; i++) {
|
||||
|
||||
size_t ss_size;
|
||||
size_t namelen = strlen(he->h_name) + 1; /* include null-terminatior */
|
||||
#ifdef ENABLE_IPV6
|
||||
if(he->h_addrtype == AF_INET6)
|
||||
ss_size = sizeof(struct sockaddr_in6);
|
||||
|
@ -303,24 +282,17 @@ Curl_he2ai(const struct hostent *he, int port)
|
|||
#endif
|
||||
ss_size = sizeof(struct sockaddr_in);
|
||||
|
||||
ai = calloc(1, sizeof(Curl_addrinfo));
|
||||
/* allocate memory to hold the struct, the address and the name */
|
||||
ai = calloc(1, sizeof(struct Curl_addrinfo) + ss_size + namelen);
|
||||
if(!ai) {
|
||||
result = CURLE_OUT_OF_MEMORY;
|
||||
break;
|
||||
}
|
||||
ai->ai_canonname = strdup(he->h_name);
|
||||
if(!ai->ai_canonname) {
|
||||
result = CURLE_OUT_OF_MEMORY;
|
||||
free(ai);
|
||||
break;
|
||||
}
|
||||
ai->ai_addr = calloc(1, ss_size);
|
||||
if(!ai->ai_addr) {
|
||||
result = CURLE_OUT_OF_MEMORY;
|
||||
free(ai->ai_canonname);
|
||||
free(ai);
|
||||
break;
|
||||
}
|
||||
/* put the address after the struct */
|
||||
ai->ai_addr = (void *)((char *)ai + sizeof(struct Curl_addrinfo));
|
||||
/* then put the name after the address */
|
||||
ai->ai_canonname = (char *)ai->ai_addr + ss_size;
|
||||
memcpy(ai->ai_canonname, he->h_name, namelen);
|
||||
|
||||
if(!firstai)
|
||||
/* store the pointer we want to return from this function */
|
||||
|
@ -393,10 +365,10 @@ struct namebuff {
|
|||
* given address/host
|
||||
*/
|
||||
|
||||
Curl_addrinfo *
|
||||
struct Curl_addrinfo *
|
||||
Curl_ip2addr(int af, const void *inaddr, const char *hostname, int port)
|
||||
{
|
||||
Curl_addrinfo *ai;
|
||||
struct Curl_addrinfo *ai;
|
||||
|
||||
#if defined(__VMS) && \
|
||||
defined(__INITIAL_POINTER_SIZE) && (__INITIAL_POINTER_SIZE == 64)
|
||||
|
@ -469,7 +441,7 @@ Curl_ip2addr(int af, const void *inaddr, const char *hostname, int port)
|
|||
* Given an IPv4 or IPv6 dotted string address, this converts it to a proper
|
||||
* allocated Curl_addrinfo struct and returns it.
|
||||
*/
|
||||
Curl_addrinfo *Curl_str2addr(char *address, int port)
|
||||
struct Curl_addrinfo *Curl_str2addr(char *address, int port)
|
||||
{
|
||||
struct in_addr in;
|
||||
if(Curl_inet_pton(AF_INET, address, &in) > 0)
|
||||
|
@ -492,22 +464,19 @@ Curl_addrinfo *Curl_str2addr(char *address, int port)
|
|||
* struct initialized with this path.
|
||||
* Set '*longpath' to TRUE if the error is a too long path.
|
||||
*/
|
||||
Curl_addrinfo *Curl_unix2addr(const char *path, bool *longpath, bool abstract)
|
||||
struct Curl_addrinfo *Curl_unix2addr(const char *path, bool *longpath,
|
||||
bool abstract)
|
||||
{
|
||||
Curl_addrinfo *ai;
|
||||
struct Curl_addrinfo *ai;
|
||||
struct sockaddr_un *sa_un;
|
||||
size_t path_len;
|
||||
|
||||
*longpath = FALSE;
|
||||
|
||||
ai = calloc(1, sizeof(Curl_addrinfo));
|
||||
ai = calloc(1, sizeof(struct Curl_addrinfo) + sizeof(struct sockaddr_un));
|
||||
if(!ai)
|
||||
return NULL;
|
||||
ai->ai_addr = calloc(1, sizeof(struct sockaddr_un));
|
||||
if(!ai->ai_addr) {
|
||||
free(ai);
|
||||
return NULL;
|
||||
}
|
||||
ai->ai_addr = (void *)((char *)ai + sizeof(struct Curl_addrinfo));
|
||||
|
||||
sa_un = (void *) ai->ai_addr;
|
||||
sa_un->sun_family = AF_UNIX;
|
||||
|
@ -515,7 +484,6 @@ Curl_addrinfo *Curl_unix2addr(const char *path, bool *longpath, bool abstract)
|
|||
/* sun_path must be able to store the NUL-terminated path */
|
||||
path_len = strlen(path) + 1;
|
||||
if(path_len > sizeof(sa_un->sun_path)) {
|
||||
free(ai->ai_addr);
|
||||
free(ai);
|
||||
*longpath = TRUE;
|
||||
return NULL;
|
||||
|
@ -598,9 +566,9 @@ curl_dbg_getaddrinfo(const char *hostname,
|
|||
* Work-arounds the sin6_port is always zero bug on iOS 9.3.2 and Mac OS X
|
||||
* 10.11.5.
|
||||
*/
|
||||
void Curl_addrinfo_set_port(Curl_addrinfo *addrinfo, int port)
|
||||
void Curl_addrinfo_set_port(struct Curl_addrinfo *addrinfo, int port)
|
||||
{
|
||||
Curl_addrinfo *ca;
|
||||
struct Curl_addrinfo *ca;
|
||||
struct sockaddr_in *addr;
|
||||
#ifdef ENABLE_IPV6
|
||||
struct sockaddr_in6 *addr6;
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -40,7 +42,6 @@
|
|||
# include <stdlib.h>
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Curl_addrinfo is our internal struct definition that we use to allow
|
||||
* consistent internal handling of this data. We use this even when the
|
||||
|
@ -58,29 +59,29 @@ struct Curl_addrinfo {
|
|||
struct sockaddr *ai_addr;
|
||||
struct Curl_addrinfo *ai_next;
|
||||
};
|
||||
typedef struct Curl_addrinfo Curl_addrinfo;
|
||||
|
||||
void
|
||||
Curl_freeaddrinfo(Curl_addrinfo *cahead);
|
||||
Curl_freeaddrinfo(struct Curl_addrinfo *cahead);
|
||||
|
||||
#ifdef HAVE_GETADDRINFO
|
||||
int
|
||||
Curl_getaddrinfo_ex(const char *nodename,
|
||||
const char *servname,
|
||||
const struct addrinfo *hints,
|
||||
Curl_addrinfo **result);
|
||||
struct Curl_addrinfo **result);
|
||||
#endif
|
||||
|
||||
Curl_addrinfo *
|
||||
struct Curl_addrinfo *
|
||||
Curl_he2ai(const struct hostent *he, int port);
|
||||
|
||||
Curl_addrinfo *
|
||||
struct Curl_addrinfo *
|
||||
Curl_ip2addr(int af, const void *inaddr, const char *hostname, int port);
|
||||
|
||||
Curl_addrinfo *Curl_str2addr(char *dotted, int port);
|
||||
struct Curl_addrinfo *Curl_str2addr(char *dotted, int port);
|
||||
|
||||
#ifdef USE_UNIX_SOCKETS
|
||||
Curl_addrinfo *Curl_unix2addr(const char *path, bool *longpath, bool abstract);
|
||||
struct Curl_addrinfo *Curl_unix2addr(const char *path, bool *longpath,
|
||||
bool abstract);
|
||||
#endif
|
||||
|
||||
#if defined(CURLDEBUG) && defined(HAVE_GETADDRINFO) && \
|
||||
|
@ -98,7 +99,7 @@ curl_dbg_getaddrinfo(const char *hostname, const char *service,
|
|||
|
||||
#ifdef HAVE_GETADDRINFO
|
||||
#ifdef USE_RESOLVE_ON_IPS
|
||||
void Curl_addrinfo_set_port(Curl_addrinfo *addrinfo, int port);
|
||||
void Curl_addrinfo_set_port(struct Curl_addrinfo *addrinfo, int port);
|
||||
#else
|
||||
#define Curl_addrinfo_set_port(x,y)
|
||||
#endif
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2014, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,15 +20,14 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
CURLcode Curl_base64_encode(struct Curl_easy *data,
|
||||
const char *inputbuff, size_t insize,
|
||||
CURLcode Curl_base64_encode(const char *inputbuff, size_t insize,
|
||||
char **outptr, size_t *outlen);
|
||||
CURLcode Curl_base64url_encode(struct Curl_easy *data,
|
||||
const char *inputbuff, size_t insize,
|
||||
CURLcode Curl_base64url_encode(const char *inputbuff, size_t insize,
|
||||
char **outptr, size_t *outlen);
|
||||
|
||||
CURLcode Curl_base64_decode(const char *src,
|
||||
unsigned char **outptr, size_t *outlen);
|
||||
|
||||
|
|
|
@ -1,60 +1,113 @@
|
|||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
/* lib/curl_config.h.in. Generated somehow by cmake. */
|
||||
|
||||
/* when building libcurl itself */
|
||||
#cmakedefine BUILDING_LIBCURL 1
|
||||
/* disables alt-svc */
|
||||
#cmakedefine CURL_DISABLE_ALTSVC 1
|
||||
|
||||
/* to disable cookies support */
|
||||
/* disables cookies support */
|
||||
#cmakedefine CURL_DISABLE_COOKIES 1
|
||||
|
||||
/* to disable cryptographic authentication */
|
||||
/* disables cryptographic authentication */
|
||||
#cmakedefine CURL_DISABLE_CRYPTO_AUTH 1
|
||||
|
||||
/* to disable DICT */
|
||||
/* disables DICT */
|
||||
#cmakedefine CURL_DISABLE_DICT 1
|
||||
|
||||
/* to disable FILE */
|
||||
/* disables DNS-over-HTTPS */
|
||||
#cmakedefine CURL_DISABLE_DOH 1
|
||||
|
||||
/* disables FILE */
|
||||
#cmakedefine CURL_DISABLE_FILE 1
|
||||
|
||||
/* to disable FTP */
|
||||
/* disables FTP */
|
||||
#cmakedefine CURL_DISABLE_FTP 1
|
||||
|
||||
/* to disable GOPHER */
|
||||
/* disables GOPHER */
|
||||
#cmakedefine CURL_DISABLE_GOPHER 1
|
||||
|
||||
/* to disable IMAP */
|
||||
#cmakedefine CURL_DISABLE_IMAP 1
|
||||
/* disables HSTS support */
|
||||
#cmakedefine CURL_DISABLE_HSTS 1
|
||||
|
||||
/* to disable HTTP */
|
||||
/* disables HTTP */
|
||||
#cmakedefine CURL_DISABLE_HTTP 1
|
||||
|
||||
/* to disable LDAP */
|
||||
/* disables IMAP */
|
||||
#cmakedefine CURL_DISABLE_IMAP 1
|
||||
|
||||
/* disables LDAP */
|
||||
#cmakedefine CURL_DISABLE_LDAP 1
|
||||
|
||||
/* to disable LDAPS */
|
||||
/* disables LDAPS */
|
||||
#cmakedefine CURL_DISABLE_LDAPS 1
|
||||
|
||||
/* to disable POP3 */
|
||||
/* disables --libcurl option from the curl tool */
|
||||
#cmakedefine CURL_DISABLE_LIBCURL_OPTION 1
|
||||
|
||||
/* disables MIME support */
|
||||
#cmakedefine CURL_DISABLE_MIME 1
|
||||
|
||||
/* disables MQTT */
|
||||
#cmakedefine CURL_DISABLE_MQTT 1
|
||||
|
||||
/* disables netrc parser */
|
||||
#cmakedefine CURL_DISABLE_NETRC 1
|
||||
|
||||
/* disables NTLM support */
|
||||
#cmakedefine CURL_DISABLE_NTLM 1
|
||||
|
||||
/* disables date parsing */
|
||||
#cmakedefine CURL_DISABLE_PARSEDATE 1
|
||||
|
||||
/* disables POP3 */
|
||||
#cmakedefine CURL_DISABLE_POP3 1
|
||||
|
||||
/* to disable proxies */
|
||||
/* disables built-in progress meter */
|
||||
#cmakedefine CURL_DISABLE_PROGRESS_METER 1
|
||||
|
||||
/* disables proxies */
|
||||
#cmakedefine CURL_DISABLE_PROXY 1
|
||||
|
||||
/* to disable RTSP */
|
||||
/* disables RTSP */
|
||||
#cmakedefine CURL_DISABLE_RTSP 1
|
||||
|
||||
/* to disable SMB */
|
||||
/* disables SMB */
|
||||
#cmakedefine CURL_DISABLE_SMB 1
|
||||
|
||||
/* to disable SMTP */
|
||||
/* disables SMTP */
|
||||
#cmakedefine CURL_DISABLE_SMTP 1
|
||||
|
||||
/* to disable TELNET */
|
||||
/* disables use of socketpair for curl_multi_poll */
|
||||
#cmakedefine CURL_DISABLE_SOCKETPAIR 1
|
||||
|
||||
/* disables TELNET */
|
||||
#cmakedefine CURL_DISABLE_TELNET 1
|
||||
|
||||
/* to disable TFTP */
|
||||
/* disables TFTP */
|
||||
#cmakedefine CURL_DISABLE_TFTP 1
|
||||
|
||||
/* to disable verbose strings */
|
||||
/* disables verbose strings */
|
||||
#cmakedefine CURL_DISABLE_VERBOSE_STRINGS 1
|
||||
|
||||
/* to make a symbol visible */
|
||||
|
@ -64,6 +117,9 @@
|
|||
#define CURL_EXTERN_SYMBOL
|
||||
#endif
|
||||
|
||||
/* Allow SMB to work on Windows */
|
||||
#cmakedefine USE_WIN32_CRYPTO 1
|
||||
|
||||
/* Use Windows LDAP implementation */
|
||||
#cmakedefine USE_WIN32_LDAP 1
|
||||
|
||||
|
@ -76,41 +132,20 @@
|
|||
/* Define if you want to enable IPv6 support */
|
||||
#cmakedefine ENABLE_IPV6 1
|
||||
|
||||
/* Define to the type qualifier of arg 1 for getnameinfo. */
|
||||
#cmakedefine GETNAMEINFO_QUAL_ARG1 ${GETNAMEINFO_QUAL_ARG1}
|
||||
|
||||
/* Define to the type of arg 1 for getnameinfo. */
|
||||
#cmakedefine GETNAMEINFO_TYPE_ARG1 ${GETNAMEINFO_TYPE_ARG1}
|
||||
|
||||
/* Define to the type of arg 2 for getnameinfo. */
|
||||
#cmakedefine GETNAMEINFO_TYPE_ARG2 ${GETNAMEINFO_TYPE_ARG2}
|
||||
|
||||
/* Define to the type of args 4 and 6 for getnameinfo. */
|
||||
#cmakedefine GETNAMEINFO_TYPE_ARG46 ${GETNAMEINFO_TYPE_ARG46}
|
||||
|
||||
/* Define to the type of arg 7 for getnameinfo. */
|
||||
#cmakedefine GETNAMEINFO_TYPE_ARG7 ${GETNAMEINFO_TYPE_ARG7}
|
||||
|
||||
/* Specifies the number of arguments to getservbyport_r */
|
||||
#cmakedefine GETSERVBYPORT_R_ARGS ${GETSERVBYPORT_R_ARGS}
|
||||
|
||||
/* Specifies the size of the buffer to pass to getservbyport_r */
|
||||
#cmakedefine GETSERVBYPORT_R_BUFSIZE ${GETSERVBYPORT_R_BUFSIZE}
|
||||
|
||||
/* Define to 1 if you have the alarm function. */
|
||||
#cmakedefine HAVE_ALARM 1
|
||||
|
||||
/* Define to 1 if you have the <alloca.h> header file. */
|
||||
#cmakedefine HAVE_ALLOCA_H 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 the <assert.h> header file. */
|
||||
#cmakedefine HAVE_ASSERT_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 `basename' function. */
|
||||
#cmakedefine HAVE_BASENAME 1
|
||||
|
@ -127,27 +162,6 @@
|
|||
/* Define to 1 if you have the `closesocket' function. */
|
||||
#cmakedefine HAVE_CLOSESOCKET 1
|
||||
|
||||
/* Define to 1 if you have the `CRYPTO_cleanup_all_ex_data' function. */
|
||||
#cmakedefine HAVE_CRYPTO_CLEANUP_ALL_EX_DATA 1
|
||||
|
||||
/* Define to 1 if you have the <crypto.h> header file. */
|
||||
#cmakedefine HAVE_CRYPTO_H 1
|
||||
|
||||
/* Define to 1 if you have the <des.h> header file. */
|
||||
#cmakedefine HAVE_DES_H 1
|
||||
|
||||
/* Define to 1 if you have the <dlfcn.h> header file. */
|
||||
#cmakedefine HAVE_DLFCN_H 1
|
||||
|
||||
/* Define to 1 if you have the `ENGINE_load_builtin_engines' function. */
|
||||
#cmakedefine HAVE_ENGINE_LOAD_BUILTIN_ENGINES 1
|
||||
|
||||
/* Define to 1 if you have the <errno.h> header file. */
|
||||
#cmakedefine HAVE_ERRNO_H 1
|
||||
|
||||
/* Define to 1 if you have the <err.h> header file. */
|
||||
#cmakedefine HAVE_ERR_H 1
|
||||
|
||||
/* Define to 1 if you have the fcntl function. */
|
||||
#cmakedefine HAVE_FCNTL 1
|
||||
|
||||
|
@ -157,44 +171,23 @@
|
|||
/* Define to 1 if you have a working fcntl O_NONBLOCK function. */
|
||||
#cmakedefine HAVE_FCNTL_O_NONBLOCK 1
|
||||
|
||||
/* Define to 1 if you have the fdopen function. */
|
||||
#cmakedefine HAVE_FDOPEN 1
|
||||
|
||||
/* Define to 1 if you have the `fork' function. */
|
||||
#cmakedefine HAVE_FORK 1
|
||||
|
||||
/* Define to 1 if you have the freeaddrinfo function. */
|
||||
#cmakedefine HAVE_FREEADDRINFO 1
|
||||
|
||||
/* Define to 1 if you have the freeifaddrs function. */
|
||||
#cmakedefine HAVE_FREEIFADDRS 1
|
||||
|
||||
/* Define to 1 if you have the ftruncate function. */
|
||||
#cmakedefine HAVE_FTRUNCATE 1
|
||||
|
||||
/* Define to 1 if you have a working getaddrinfo function. */
|
||||
#cmakedefine HAVE_GETADDRINFO 1
|
||||
|
||||
/* Define to 1 if the getaddrinfo function is threadsafe. */
|
||||
#cmakedefine HAVE_GETADDRINFO_THREADSAFE 1
|
||||
|
||||
/* Define to 1 if you have the `geteuid' function. */
|
||||
#cmakedefine HAVE_GETEUID 1
|
||||
|
||||
/* Define to 1 if you have the gethostbyaddr function. */
|
||||
#cmakedefine HAVE_GETHOSTBYADDR 1
|
||||
|
||||
/* Define to 1 if you have the gethostbyaddr_r function. */
|
||||
#cmakedefine HAVE_GETHOSTBYADDR_R 1
|
||||
|
||||
/* gethostbyaddr_r() takes 5 args */
|
||||
#cmakedefine HAVE_GETHOSTBYADDR_R_5 1
|
||||
|
||||
/* gethostbyaddr_r() takes 7 args */
|
||||
#cmakedefine HAVE_GETHOSTBYADDR_R_7 1
|
||||
|
||||
/* gethostbyaddr_r() takes 8 args */
|
||||
#cmakedefine HAVE_GETHOSTBYADDR_R_8 1
|
||||
|
||||
/* Define to 1 if you have the gethostbyname function. */
|
||||
#cmakedefine HAVE_GETHOSTBYNAME 1
|
||||
/* Define to 1 if you have the `getppid' function. */
|
||||
#cmakedefine HAVE_GETPPID 1
|
||||
|
||||
/* Define to 1 if you have the gethostbyname_r function. */
|
||||
#cmakedefine HAVE_GETHOSTBYNAME_R 1
|
||||
|
@ -214,24 +207,21 @@
|
|||
/* Define to 1 if you have a working getifaddrs function. */
|
||||
#cmakedefine HAVE_GETIFADDRS 1
|
||||
|
||||
/* Define to 1 if you have the getnameinfo function. */
|
||||
#cmakedefine HAVE_GETNAMEINFO 1
|
||||
|
||||
/* 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 `getprotobyname' function. */
|
||||
#cmakedefine HAVE_GETPROTOBYNAME 1
|
||||
|
||||
/* Define to 1 if you have the `getpeername' function. */
|
||||
#cmakedefine HAVE_GETPEERNAME 1
|
||||
|
||||
/* Define to 1 if you have the `getsockname' function. */
|
||||
#cmakedefine HAVE_GETSOCKNAME 1
|
||||
|
||||
/* Define to 1 if you have the `if_nametoindex' function. */
|
||||
#cmakedefine HAVE_IF_NAMETOINDEX 1
|
||||
|
||||
/* Define to 1 if you have the `getpwuid' function. */
|
||||
#cmakedefine HAVE_GETPWUID 1
|
||||
|
||||
|
@ -241,9 +231,6 @@
|
|||
/* Define to 1 if you have the `getrlimit' function. */
|
||||
#cmakedefine HAVE_GETRLIMIT 1
|
||||
|
||||
/* Define to 1 if you have the getservbyport_r function. */
|
||||
#cmakedefine HAVE_GETSERVBYPORT_R 1
|
||||
|
||||
/* Define to 1 if you have the `gettimeofday' function. */
|
||||
#cmakedefine HAVE_GETTIMEOFDAY 1
|
||||
|
||||
|
@ -277,39 +264,24 @@
|
|||
/* Define to 1 if you have the `idna_strerror' function. */
|
||||
#cmakedefine HAVE_IDNA_STRERROR 1
|
||||
|
||||
/* Define to 1 if you have the `idn_free' function. */
|
||||
#cmakedefine HAVE_IDN_FREE 1
|
||||
|
||||
/* Define to 1 if you have the <idn-free.h> header file. */
|
||||
#cmakedefine HAVE_IDN_FREE_H 1
|
||||
|
||||
/* Define to 1 if you have the <ifaddrs.h> header file. */
|
||||
#cmakedefine HAVE_IFADDRS_H 1
|
||||
|
||||
/* Define to 1 if you have the `inet_addr' function. */
|
||||
#cmakedefine HAVE_INET_ADDR 1
|
||||
|
||||
/* Define to 1 if you have the inet_ntoa_r function. */
|
||||
#cmakedefine HAVE_INET_NTOA_R 1
|
||||
|
||||
/* inet_ntoa_r() takes 2 args */
|
||||
#cmakedefine HAVE_INET_NTOA_R_2 1
|
||||
|
||||
/* inet_ntoa_r() takes 3 args */
|
||||
#cmakedefine HAVE_INET_NTOA_R_3 1
|
||||
|
||||
/* Define to 1 if you have a IPv6 capable working inet_ntop function. */
|
||||
#cmakedefine HAVE_INET_NTOP 1
|
||||
|
||||
/* Define to 1 if you have a IPv6 capable working inet_pton function. */
|
||||
#cmakedefine HAVE_INET_PTON 1
|
||||
|
||||
/* Define to 1 if symbol `sa_family_t' exists */
|
||||
#cmakedefine HAVE_SA_FAMILY_T 1
|
||||
|
||||
/* Define to 1 if symbol `ADDRESS_FAMILY' exists */
|
||||
#cmakedefine HAVE_ADDRESS_FAMILY 1
|
||||
|
||||
/* Define to 1 if you have the <inttypes.h> header file. */
|
||||
#cmakedefine HAVE_INTTYPES_H 1
|
||||
|
||||
/* Define to 1 if you have the ioctl function. */
|
||||
#cmakedefine HAVE_IOCTL 1
|
||||
|
||||
/* Define to 1 if you have the ioctlsocket function. */
|
||||
#cmakedefine HAVE_IOCTLSOCKET 1
|
||||
|
||||
|
@ -332,21 +304,9 @@
|
|||
/* Define to 1 if you have the <io.h> header file. */
|
||||
#cmakedefine HAVE_IO_H 1
|
||||
|
||||
/* if you have the Kerberos4 libraries (including -ldes) */
|
||||
#cmakedefine HAVE_KRB4 1
|
||||
|
||||
/* Define to 1 if you have the `krb_get_our_ip_for_realm' function. */
|
||||
#cmakedefine HAVE_KRB_GET_OUR_IP_FOR_REALM 1
|
||||
|
||||
/* Define to 1 if you have the <krb.h> header file. */
|
||||
#cmakedefine HAVE_KRB_H 1
|
||||
|
||||
/* Define to 1 if you have the lber.h header file. */
|
||||
#cmakedefine HAVE_LBER_H 1
|
||||
|
||||
/* Define to 1 if you have the ldapssl.h header file. */
|
||||
#cmakedefine HAVE_LDAPSSL_H 1
|
||||
|
||||
/* Define to 1 if you have the ldap.h header file. */
|
||||
#cmakedefine HAVE_LDAP_H 1
|
||||
|
||||
|
@ -362,14 +322,11 @@
|
|||
/* Define to 1 if you have the <libgen.h> header file. */
|
||||
#cmakedefine HAVE_LIBGEN_H 1
|
||||
|
||||
/* Define to 1 if you have the `idn' library (-lidn). */
|
||||
#cmakedefine HAVE_LIBIDN 1
|
||||
/* Define to 1 if you have the `idn2' library (-lidn2). */
|
||||
#cmakedefine HAVE_LIBIDN2 1
|
||||
|
||||
/* Define to 1 if you have the `resolv' library (-lresolv). */
|
||||
#cmakedefine HAVE_LIBRESOLV 1
|
||||
|
||||
/* Define to 1 if you have the `resolve' library (-lresolve). */
|
||||
#cmakedefine HAVE_LIBRESOLVE 1
|
||||
/* Define to 1 if you have the idn2.h header file. */
|
||||
#cmakedefine HAVE_IDN2_H 1
|
||||
|
||||
/* Define to 1 if you have the `socket' library (-lsocket). */
|
||||
#cmakedefine HAVE_LIBSOCKET 1
|
||||
|
@ -377,27 +334,6 @@
|
|||
/* Define to 1 if you have the `ssh2' library (-lssh2). */
|
||||
#cmakedefine HAVE_LIBSSH2 1
|
||||
|
||||
/* Define to 1 if libssh2 provides `libssh2_version'. */
|
||||
#cmakedefine HAVE_LIBSSH2_VERSION 1
|
||||
|
||||
/* Define to 1 if libssh2 provides `libssh2_init'. */
|
||||
#cmakedefine HAVE_LIBSSH2_INIT 1
|
||||
|
||||
/* Define to 1 if libssh2 provides `libssh2_exit'. */
|
||||
#cmakedefine HAVE_LIBSSH2_EXIT 1
|
||||
|
||||
/* Define to 1 if libssh2 provides `libssh2_scp_send64'. */
|
||||
#cmakedefine HAVE_LIBSSH2_SCP_SEND64 1
|
||||
|
||||
/* Define to 1 if libssh2 provides `libssh2_session_handshake'. */
|
||||
#cmakedefine HAVE_LIBSSH2_SESSION_HANDSHAKE 1
|
||||
|
||||
/* Define to 1 if you have the <libssh2.h> header file. */
|
||||
#cmakedefine HAVE_LIBSSH2_H 1
|
||||
|
||||
/* Define to 1 if you have the `ssl' library (-lssl). */
|
||||
#cmakedefine HAVE_LIBSSL 1
|
||||
|
||||
/* if zlib is available */
|
||||
#cmakedefine HAVE_LIBZ 1
|
||||
|
||||
|
@ -407,21 +343,15 @@
|
|||
/* if your compiler supports LL */
|
||||
#cmakedefine HAVE_LL 1
|
||||
|
||||
/* if zstd is available */
|
||||
#cmakedefine HAVE_ZSTD 1
|
||||
|
||||
/* Define to 1 if you have the <locale.h> header file. */
|
||||
#cmakedefine HAVE_LOCALE_H 1
|
||||
|
||||
/* Define to 1 if you have a working localtime_r function. */
|
||||
#cmakedefine HAVE_LOCALTIME_R 1
|
||||
|
||||
/* Define to 1 if the compiler supports the 'long long' data type. */
|
||||
#cmakedefine HAVE_LONGLONG 1
|
||||
|
||||
/* Define to 1 if you have the malloc.h header file. */
|
||||
#cmakedefine HAVE_MALLOC_H 1
|
||||
|
||||
/* Define to 1 if you have the <memory.h> header file. */
|
||||
#cmakedefine HAVE_MEMORY_H 1
|
||||
|
||||
/* Define to 1 if you have the MSG_NOSIGNAL flag. */
|
||||
#cmakedefine HAVE_MSG_NOSIGNAL 1
|
||||
|
||||
|
@ -434,51 +364,18 @@
|
|||
/* 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 <linux/tcp.h> header file. */
|
||||
#cmakedefine HAVE_LINUX_TCP_H 1
|
||||
|
||||
/* Define to 1 if you have the <net/if.h> header file. */
|
||||
#cmakedefine HAVE_NET_IF_H 1
|
||||
|
||||
/* Define to 1 if NI_WITHSCOPEID exists and works. */
|
||||
#cmakedefine HAVE_NI_WITHSCOPEID 1
|
||||
|
||||
/* if you have an old MIT gssapi library, lacking GSS_C_NT_HOSTBASED_SERVICE */
|
||||
#cmakedefine HAVE_OLD_GSSMIT 1
|
||||
|
||||
/* Define to 1 if you have the <openssl/crypto.h> header file. */
|
||||
#cmakedefine HAVE_OPENSSL_CRYPTO_H 1
|
||||
|
||||
/* Define to 1 if you have the <openssl/engine.h> header file. */
|
||||
#cmakedefine HAVE_OPENSSL_ENGINE_H 1
|
||||
|
||||
/* Define to 1 if you have the <openssl/err.h> header file. */
|
||||
#cmakedefine HAVE_OPENSSL_ERR_H 1
|
||||
|
||||
/* Define to 1 if you have the <openssl/pem.h> header file. */
|
||||
#cmakedefine HAVE_OPENSSL_PEM_H 1
|
||||
|
||||
/* Define to 1 if you have the <openssl/pkcs12.h> header file. */
|
||||
#cmakedefine HAVE_OPENSSL_PKCS12_H 1
|
||||
|
||||
/* Define to 1 if you have the <openssl/rsa.h> header file. */
|
||||
#cmakedefine HAVE_OPENSSL_RSA_H 1
|
||||
|
||||
/* Define to 1 if you have the <openssl/ssl.h> header file. */
|
||||
#cmakedefine HAVE_OPENSSL_SSL_H 1
|
||||
|
||||
/* Define to 1 if you have the <openssl/x509.h> header file. */
|
||||
#cmakedefine HAVE_OPENSSL_X509_H 1
|
||||
|
||||
/* Define to 1 if you have the <pem.h> header file. */
|
||||
#cmakedefine HAVE_PEM_H 1
|
||||
|
||||
/* Define to 1 if you have the `perror' function. */
|
||||
#cmakedefine HAVE_PERROR 1
|
||||
|
||||
/* Define to 1 if you have the `pipe' function. */
|
||||
#cmakedefine HAVE_PIPE 1
|
||||
|
||||
/* Define to 1 if you have a working poll function. */
|
||||
#cmakedefine HAVE_POLL 1
|
||||
|
||||
/* If you have a fine poll */
|
||||
#cmakedefine HAVE_POLL_FINE 1
|
||||
|
||||
|
@ -497,21 +394,9 @@
|
|||
/* Define to 1 if you have the `RAND_egd' function. */
|
||||
#cmakedefine HAVE_RAND_EGD 1
|
||||
|
||||
/* Define to 1 if you have the `RAND_screen' function. */
|
||||
#cmakedefine HAVE_RAND_SCREEN 1
|
||||
|
||||
/* Define to 1 if you have the `RAND_status' function. */
|
||||
#cmakedefine HAVE_RAND_STATUS 1
|
||||
|
||||
/* Define to 1 if you have the recv function. */
|
||||
#cmakedefine HAVE_RECV 1
|
||||
|
||||
/* Define to 1 if you have the recvfrom function. */
|
||||
#cmakedefine HAVE_RECVFROM 1
|
||||
|
||||
/* Define to 1 if you have the <rsa.h> header file. */
|
||||
#cmakedefine HAVE_RSA_H 1
|
||||
|
||||
/* Define to 1 if you have the select function. */
|
||||
#cmakedefine HAVE_SELECT 1
|
||||
|
||||
|
@ -539,15 +424,9 @@
|
|||
/* Define to 1 if you have the `setrlimit' function. */
|
||||
#cmakedefine HAVE_SETRLIMIT 1
|
||||
|
||||
/* Define to 1 if you have the setsockopt function. */
|
||||
#cmakedefine HAVE_SETSOCKOPT 1
|
||||
|
||||
/* Define to 1 if you have a working setsockopt SO_NONBLOCK function. */
|
||||
#cmakedefine HAVE_SETSOCKOPT_SO_NONBLOCK 1
|
||||
|
||||
/* Define to 1 if you have the <sgtty.h> header file. */
|
||||
#cmakedefine HAVE_SGTTY_H 1
|
||||
|
||||
/* Define to 1 if you have the sigaction function. */
|
||||
#cmakedefine HAVE_SIGACTION 1
|
||||
|
||||
|
@ -563,42 +442,33 @@
|
|||
/* Define to 1 if you have the sigsetjmp function or macro. */
|
||||
#cmakedefine HAVE_SIGSETJMP 1
|
||||
|
||||
/* Define to 1 if sig_atomic_t is an available typedef. */
|
||||
#cmakedefine HAVE_SIG_ATOMIC_T 1
|
||||
|
||||
/* Define to 1 if sig_atomic_t is already defined as volatile. */
|
||||
#cmakedefine HAVE_SIG_ATOMIC_T_VOLATILE 1
|
||||
|
||||
/* Define to 1 if struct sockaddr_in6 has the sin6_scope_id member */
|
||||
#cmakedefine HAVE_SOCKADDR_IN6_SIN6_SCOPE_ID 1
|
||||
|
||||
/* Define to 1 if you have the `socket' function. */
|
||||
#cmakedefine HAVE_SOCKET 1
|
||||
|
||||
/* Define to 1 if you have the `SSL_get_shutdown' function. */
|
||||
#cmakedefine HAVE_SSL_GET_SHUTDOWN 1
|
||||
/* Define to 1 if you have the socketpair function. */
|
||||
#cmakedefine HAVE_SOCKETPAIR 1
|
||||
|
||||
/* Define to 1 if you have the <ssl.h> header file. */
|
||||
#cmakedefine HAVE_SSL_H 1
|
||||
|
||||
/* Define to 1 if you have the <stdatomic.h> header file. */
|
||||
#cmakedefine HAVE_STDATOMIC_H 1
|
||||
|
||||
/* Define to 1 if you have the <stdbool.h> header file. */
|
||||
#cmakedefine HAVE_STDBOOL_H 1
|
||||
|
||||
/* Define to 1 if you have the <stdint.h> header file. */
|
||||
#cmakedefine HAVE_STDINT_H 1
|
||||
|
||||
/* Define to 1 if you have the <stdio.h> header file. */
|
||||
#cmakedefine HAVE_STDIO_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
|
||||
|
||||
/* Define to 1 if you have the strcasestr function. */
|
||||
#cmakedefine HAVE_STRCASESTR 1
|
||||
|
||||
/* Define to 1 if you have the strcmpi function. */
|
||||
#cmakedefine HAVE_STRCMPI 1
|
||||
|
||||
|
@ -617,27 +487,9 @@
|
|||
/* Define to 1 if you have the <string.h> header file. */
|
||||
#cmakedefine HAVE_STRING_H 1
|
||||
|
||||
/* Define to 1 if you have the strlcat function. */
|
||||
#cmakedefine HAVE_STRLCAT 1
|
||||
|
||||
/* Define to 1 if you have the `strlcpy' function. */
|
||||
#cmakedefine HAVE_STRLCPY 1
|
||||
|
||||
/* Define to 1 if you have the strncasecmp function. */
|
||||
#cmakedefine HAVE_STRNCASECMP 1
|
||||
|
||||
/* Define to 1 if you have the strncmpi function. */
|
||||
#cmakedefine HAVE_STRNCMPI 1
|
||||
|
||||
/* Define to 1 if you have the strnicmp function. */
|
||||
#cmakedefine HAVE_STRNICMP 1
|
||||
|
||||
/* Define to 1 if you have the <stropts.h> header file. */
|
||||
#cmakedefine HAVE_STROPTS_H 1
|
||||
|
||||
/* Define to 1 if you have the strstr function. */
|
||||
#cmakedefine HAVE_STRSTR 1
|
||||
|
||||
/* Define to 1 if you have the strtok_r function. */
|
||||
#cmakedefine HAVE_STRTOK_R 1
|
||||
|
||||
|
@ -683,9 +535,6 @@
|
|||
/* Define to 1 if you have the <sys/types.h> header file. */
|
||||
#cmakedefine HAVE_SYS_TYPES_H 1
|
||||
|
||||
/* Define to 1 if you have the <sys/uio.h> header file. */
|
||||
#cmakedefine HAVE_SYS_UIO_H 1
|
||||
|
||||
/* Define to 1 if you have the <sys/un.h> header file. */
|
||||
#cmakedefine HAVE_SYS_UN_H 1
|
||||
|
||||
|
@ -701,21 +550,15 @@
|
|||
/* Define to 1 if you have the <time.h> header file. */
|
||||
#cmakedefine HAVE_TIME_H 1
|
||||
|
||||
/* Define to 1 if you have the <tld.h> header file. */
|
||||
#cmakedefine HAVE_TLD_H 1
|
||||
|
||||
/* Define to 1 if you have the `tld_strerror' function. */
|
||||
#cmakedefine HAVE_TLD_STRERROR 1
|
||||
|
||||
/* Define to 1 if you have the `uname' function. */
|
||||
#cmakedefine HAVE_UNAME 1
|
||||
|
||||
/* Define to 1 if you have the <unistd.h> header file. */
|
||||
#cmakedefine HAVE_UNISTD_H 1
|
||||
|
||||
/* Define to 1 if you have the `utime' function. */
|
||||
#cmakedefine HAVE_UTIME 1
|
||||
|
||||
/* Define to 1 if you have the `utimes' function. */
|
||||
#cmakedefine HAVE_UTIMES 1
|
||||
|
||||
/* Define to 1 if you have the <utime.h> header file. */
|
||||
#cmakedefine HAVE_UTIME_H 1
|
||||
|
||||
|
@ -725,9 +568,6 @@
|
|||
/* Define to 1 if compiler supports old gcc variadic macro style. */
|
||||
#cmakedefine HAVE_VARIADIC_MACROS_GCC 1
|
||||
|
||||
/* Define to 1 if you have the winber.h header file. */
|
||||
#cmakedefine HAVE_WINBER_H 1
|
||||
|
||||
/* Define to 1 if you have the windows.h header file. */
|
||||
#cmakedefine HAVE_WINDOWS_H 1
|
||||
|
||||
|
@ -737,34 +577,12 @@
|
|||
/* Define to 1 if you have the winsock2.h header file. */
|
||||
#cmakedefine HAVE_WINSOCK2_H 1
|
||||
|
||||
/* Define to 1 if you have the winsock.h header file. */
|
||||
#cmakedefine HAVE_WINSOCK_H 1
|
||||
|
||||
/* Define this symbol if your OS supports changing the contents of argv */
|
||||
#cmakedefine HAVE_WRITABLE_ARGV 1
|
||||
|
||||
/* Define to 1 if you have the writev function. */
|
||||
#cmakedefine HAVE_WRITEV 1
|
||||
|
||||
/* Define to 1 if you have the ws2tcpip.h header file. */
|
||||
#cmakedefine HAVE_WS2TCPIP_H 1
|
||||
|
||||
/* Define to 1 if you have the <x509.h> header file. */
|
||||
#cmakedefine HAVE_X509_H 1
|
||||
|
||||
/* Define if you have the <process.h> header file. */
|
||||
#cmakedefine HAVE_PROCESS_H 1
|
||||
|
||||
/* if you have the zlib.h header file */
|
||||
#cmakedefine HAVE_ZLIB_H 1
|
||||
|
||||
/* Define to the sub-directory in which libtool stores uninstalled libraries.
|
||||
*/
|
||||
#cmakedefine LT_OBJDIR ${LT_OBJDIR}
|
||||
|
||||
/* If you lack a fine basename() prototype */
|
||||
#cmakedefine NEED_BASENAME_PROTO 1
|
||||
|
||||
/* Define to 1 if you need the lber.h header file even with ldap.h */
|
||||
#cmakedefine NEED_LBER_H 1
|
||||
|
||||
|
@ -798,123 +616,48 @@
|
|||
/* a suitable file to read random data from */
|
||||
#cmakedefine RANDOM_FILE "${RANDOM_FILE}"
|
||||
|
||||
/* Define to the type of arg 1 for recvfrom. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG1 ${RECVFROM_TYPE_ARG1}
|
||||
/*
|
||||
Note: SIZEOF_* variables are fetched with CMake through check_type_size().
|
||||
As per CMake documentation on CheckTypeSize, C preprocessor code is
|
||||
generated by CMake into SIZEOF_*_CODE. This is what we use in the
|
||||
following statements.
|
||||
|
||||
/* Define to the type pointed by arg 2 for recvfrom. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG2 ${RECVFROM_TYPE_ARG2}
|
||||
|
||||
/* Define to 1 if the type pointed by arg 2 for recvfrom is void. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG2_IS_VOID 1
|
||||
|
||||
/* Define to the type of arg 3 for recvfrom. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG3 ${RECVFROM_TYPE_ARG3}
|
||||
|
||||
/* Define to the type of arg 4 for recvfrom. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG4 ${RECVFROM_TYPE_ARG4}
|
||||
|
||||
/* Define to the type pointed by arg 5 for recvfrom. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG5 ${RECVFROM_TYPE_ARG5}
|
||||
|
||||
/* Define to 1 if the type pointed by arg 5 for recvfrom is void. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG5_IS_VOID 1
|
||||
|
||||
/* Define to the type pointed by arg 6 for recvfrom. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG6 ${RECVFROM_TYPE_ARG6}
|
||||
|
||||
/* Define to 1 if the type pointed by arg 6 for recvfrom is void. */
|
||||
#cmakedefine RECVFROM_TYPE_ARG6_IS_VOID 1
|
||||
|
||||
/* Define to the function return type for recvfrom. */
|
||||
#cmakedefine RECVFROM_TYPE_RETV ${RECVFROM_TYPE_RETV}
|
||||
|
||||
/* Define to the type of arg 1 for recv. */
|
||||
#cmakedefine RECV_TYPE_ARG1 ${RECV_TYPE_ARG1}
|
||||
|
||||
/* Define to the type of arg 2 for recv. */
|
||||
#cmakedefine RECV_TYPE_ARG2 ${RECV_TYPE_ARG2}
|
||||
|
||||
/* Define to the type of arg 3 for recv. */
|
||||
#cmakedefine RECV_TYPE_ARG3 ${RECV_TYPE_ARG3}
|
||||
|
||||
/* Define to the type of arg 4 for recv. */
|
||||
#cmakedefine RECV_TYPE_ARG4 ${RECV_TYPE_ARG4}
|
||||
|
||||
/* Define to the function return type for recv. */
|
||||
#cmakedefine RECV_TYPE_RETV ${RECV_TYPE_RETV}
|
||||
|
||||
/* Define as the return type of signal handlers (`int' or `void'). */
|
||||
#cmakedefine RETSIGTYPE ${RETSIGTYPE}
|
||||
|
||||
/* Define to the type qualifier of arg 5 for select. */
|
||||
#cmakedefine SELECT_QUAL_ARG5 ${SELECT_QUAL_ARG5}
|
||||
|
||||
/* Define to the type of arg 1 for select. */
|
||||
#cmakedefine SELECT_TYPE_ARG1 ${SELECT_TYPE_ARG1}
|
||||
|
||||
/* Define to the type of args 2, 3 and 4 for select. */
|
||||
#cmakedefine SELECT_TYPE_ARG234 ${SELECT_TYPE_ARG234}
|
||||
|
||||
/* Define to the type of arg 5 for select. */
|
||||
#cmakedefine SELECT_TYPE_ARG5 ${SELECT_TYPE_ARG5}
|
||||
|
||||
/* Define to the function return type for select. */
|
||||
#cmakedefine SELECT_TYPE_RETV ${SELECT_TYPE_RETV}
|
||||
|
||||
/* Define to the type qualifier of arg 2 for send. */
|
||||
#cmakedefine SEND_QUAL_ARG2 ${SEND_QUAL_ARG2}
|
||||
|
||||
/* Define to the type of arg 1 for send. */
|
||||
#cmakedefine SEND_TYPE_ARG1 ${SEND_TYPE_ARG1}
|
||||
|
||||
/* Define to the type of arg 2 for send. */
|
||||
#cmakedefine SEND_TYPE_ARG2 ${SEND_TYPE_ARG2}
|
||||
|
||||
/* Define to the type of arg 3 for send. */
|
||||
#cmakedefine SEND_TYPE_ARG3 ${SEND_TYPE_ARG3}
|
||||
|
||||
/* Define to the type of arg 4 for send. */
|
||||
#cmakedefine SEND_TYPE_ARG4 ${SEND_TYPE_ARG4}
|
||||
|
||||
/* Define to the function return type for send. */
|
||||
#cmakedefine SEND_TYPE_RETV ${SEND_TYPE_RETV}
|
||||
Reference: https://cmake.org/cmake/help/latest/module/CheckTypeSize.html
|
||||
*/
|
||||
|
||||
/* The size of `int', as computed by sizeof. */
|
||||
@SIZEOF_INT_CODE@
|
||||
${SIZEOF_INT_CODE}
|
||||
|
||||
/* The size of `short', as computed by sizeof. */
|
||||
@SIZEOF_SHORT_CODE@
|
||||
${SIZEOF_SHORT_CODE}
|
||||
|
||||
/* The size of `long', as computed by sizeof. */
|
||||
@SIZEOF_LONG_CODE@
|
||||
${SIZEOF_LONG_CODE}
|
||||
|
||||
/* The size of `long long', as computed by sizeof. */
|
||||
@SIZEOF_LONG_LONG_CODE@
|
||||
${SIZEOF_LONG_LONG_CODE}
|
||||
|
||||
/* The size of `__int64', as computed by sizeof. */
|
||||
@SIZEOF___INT64_CODE@
|
||||
${SIZEOF___INT64_CODE}
|
||||
|
||||
/* The size of `off_t', as computed by sizeof. */
|
||||
@SIZEOF_OFF_T_CODE@
|
||||
${SIZEOF_OFF_T_CODE}
|
||||
|
||||
/* The size of `curl_off_t', as computed by sizeof. */
|
||||
@SIZEOF_CURL_OFF_T_CODE@
|
||||
${SIZEOF_CURL_OFF_T_CODE}
|
||||
|
||||
/* The size of `size_t', as computed by sizeof. */
|
||||
@SIZEOF_SIZE_T_CODE@
|
||||
${SIZEOF_SIZE_T_CODE}
|
||||
|
||||
/* The size of `ssize_t', as computed by sizeof. */
|
||||
@SIZEOF_SSIZE_T_CODE@
|
||||
${SIZEOF_SSIZE_T_CODE}
|
||||
|
||||
/* The size of `time_t', as computed by sizeof. */
|
||||
@SIZEOF_TIME_T_CODE@
|
||||
${SIZEOF_TIME_T_CODE}
|
||||
|
||||
/* Define to 1 if you have the ANSI C header files. */
|
||||
#cmakedefine STDC_HEADERS 1
|
||||
|
||||
/* Define to the type of arg 3 for strerror_r. */
|
||||
#cmakedefine STRERROR_R_TYPE_ARG3 ${STRERROR_R_TYPE_ARG3}
|
||||
|
||||
/* Define to 1 if you can safely include both <sys/time.h> and <time.h>. */
|
||||
#cmakedefine TIME_WITH_SYS_TIME 1
|
||||
|
||||
|
@ -927,39 +670,67 @@
|
|||
/* Define if you want to enable WIN32 threaded DNS lookup */
|
||||
#cmakedefine USE_THREADS_WIN32 1
|
||||
|
||||
/* Define to disable non-blocking sockets. */
|
||||
#cmakedefine USE_BLOCKING_SOCKETS 1
|
||||
|
||||
/* if GnuTLS is enabled */
|
||||
#cmakedefine USE_GNUTLS 1
|
||||
|
||||
/* if PolarSSL is enabled */
|
||||
#cmakedefine USE_POLARSSL 1
|
||||
|
||||
/* if Secure Transport is enabled */
|
||||
#cmakedefine USE_SECTRANSP 1
|
||||
|
||||
/* if mbedTLS is enabled */
|
||||
#cmakedefine USE_MBEDTLS 1
|
||||
|
||||
/* if BearSSL is enabled */
|
||||
#cmakedefine USE_BEARSSL 1
|
||||
|
||||
/* if WolfSSL is enabled */
|
||||
#cmakedefine USE_WOLFSSL 1
|
||||
|
||||
/* if libSSH is in use */
|
||||
#cmakedefine USE_LIBSSH 1
|
||||
|
||||
/* if libSSH2 is in use */
|
||||
#cmakedefine USE_LIBSSH2 1
|
||||
|
||||
/* if libPSL is in use */
|
||||
#cmakedefine USE_LIBPSL 1
|
||||
|
||||
/* If you want to build curl with the built-in manual */
|
||||
#cmakedefine USE_MANUAL 1
|
||||
|
||||
/* if NSS is enabled */
|
||||
#cmakedefine USE_NSS 1
|
||||
|
||||
/* if you have the PK11_CreateManagedGenericObject function */
|
||||
#cmakedefine HAVE_PK11_CREATEMANAGEDGENERICOBJECT 1
|
||||
|
||||
/* if you want to use OpenLDAP code instead of legacy ldap implementation */
|
||||
#cmakedefine USE_OPENLDAP 1
|
||||
|
||||
/* if OpenSSL is in use */
|
||||
#cmakedefine USE_OPENSSL 1
|
||||
|
||||
/* Define to 1 if you don't want the OpenSSL configuration to be loaded
|
||||
automatically */
|
||||
#cmakedefine CURL_DISABLE_OPENSSL_AUTO_LOAD_CONFIG 1
|
||||
|
||||
/* to enable NGHTTP2 */
|
||||
#cmakedefine USE_NGHTTP2 1
|
||||
|
||||
/* to enable NGTCP2 */
|
||||
#cmakedefine USE_NGTCP2 1
|
||||
|
||||
/* to enable NGHTTP3 */
|
||||
#cmakedefine USE_NGHTTP3 1
|
||||
|
||||
/* to enable quiche */
|
||||
#cmakedefine USE_QUICHE 1
|
||||
|
||||
/* Define to 1 if you have the quiche_conn_set_qlog_fd function. */
|
||||
#cmakedefine HAVE_QUICHE_CONN_SET_QLOG_FD 1
|
||||
|
||||
/* to enable msh3 */
|
||||
#cmakedefine USE_MSH3 1
|
||||
|
||||
/* if Unix domain sockets are enabled */
|
||||
#cmakedefine USE_UNIX_SOCKETS
|
||||
|
||||
|
@ -972,9 +743,6 @@
|
|||
/* enable multiple SSL backends */
|
||||
#cmakedefine CURL_WITH_MULTI_SSL 1
|
||||
|
||||
/* Define to 1 if using yaSSL in OpenSSL compatibility mode. */
|
||||
#cmakedefine USE_YASSLEMUL 1
|
||||
|
||||
/* Version number of package */
|
||||
#cmakedefine VERSION ${VERSION}
|
||||
|
||||
|
@ -1022,3 +790,9 @@
|
|||
|
||||
/* Define to 1 if you have the mach_absolute_time function. */
|
||||
#cmakedefine HAVE_MACH_ABSOLUTE_TIME 1
|
||||
|
||||
/* to enable Windows IDN */
|
||||
#cmakedefine USE_WIN32_IDN 1
|
||||
|
||||
/* Define to 1 to enable websocket support. */
|
||||
#cmakedefine USE_WEBSOCKETS 1
|
||||
|
|
|
@ -1,133 +0,0 @@
|
|||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2018, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#ifndef CURL_DOES_CONVERSIONS
|
||||
|
||||
#undef _U
|
||||
#define _U (1<<0) /* upper case */
|
||||
#undef _L
|
||||
#define _L (1<<1) /* lower case */
|
||||
#undef _N
|
||||
#define _N (1<<2) /* decimal numerical digit */
|
||||
#undef _S
|
||||
#define _S (1<<3) /* space */
|
||||
#undef _P
|
||||
#define _P (1<<4) /* punctuation */
|
||||
#undef _C
|
||||
#define _C (1<<5) /* control */
|
||||
#undef _X
|
||||
#define _X (1<<6) /* hexadecimal letter */
|
||||
#undef _B
|
||||
#define _B (1<<7) /* blank */
|
||||
|
||||
static const unsigned char ascii[128] = {
|
||||
_C, _C, _C, _C, _C, _C, _C, _C,
|
||||
_C, _C|_S, _C|_S, _C|_S, _C|_S, _C|_S, _C, _C,
|
||||
_C, _C, _C, _C, _C, _C, _C, _C,
|
||||
_C, _C, _C, _C, _C, _C, _C, _C,
|
||||
_S|_B, _P, _P, _P, _P, _P, _P, _P,
|
||||
_P, _P, _P, _P, _P, _P, _P, _P,
|
||||
_N, _N, _N, _N, _N, _N, _N, _N,
|
||||
_N, _N, _P, _P, _P, _P, _P, _P,
|
||||
_P, _U|_X, _U|_X, _U|_X, _U|_X, _U|_X, _U|_X, _U,
|
||||
_U, _U, _U, _U, _U, _U, _U, _U,
|
||||
_U, _U, _U, _U, _U, _U, _U, _U,
|
||||
_U, _U, _U, _P, _P, _P, _P, _P,
|
||||
_P, _L|_X, _L|_X, _L|_X, _L|_X, _L|_X, _L|_X, _L,
|
||||
_L, _L, _L, _L, _L, _L, _L, _L,
|
||||
_L, _L, _L, _L, _L, _L, _L, _L,
|
||||
_L, _L, _L, _P, _P, _P, _P, _C
|
||||
};
|
||||
|
||||
int Curl_isspace(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & _S);
|
||||
}
|
||||
|
||||
int Curl_isdigit(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & _N);
|
||||
}
|
||||
|
||||
int Curl_isalnum(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & (_N|_U|_L));
|
||||
}
|
||||
|
||||
int Curl_isxdigit(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & (_N|_X));
|
||||
}
|
||||
|
||||
int Curl_isgraph(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80) || (c == ' '))
|
||||
return FALSE;
|
||||
return (ascii[c] & (_N|_X|_U|_L|_P|_S));
|
||||
}
|
||||
|
||||
int Curl_isprint(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & (_N|_X|_U|_L|_P|_S));
|
||||
}
|
||||
|
||||
int Curl_isalpha(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & (_U|_L));
|
||||
}
|
||||
|
||||
int Curl_isupper(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & (_U));
|
||||
}
|
||||
|
||||
int Curl_islower(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & (_L));
|
||||
}
|
||||
|
||||
int Curl_iscntrl(int c)
|
||||
{
|
||||
if((c < 0) || (c >= 0x80))
|
||||
return FALSE;
|
||||
return (ascii[c] & (_C));
|
||||
}
|
||||
|
||||
#endif /* !CURL_DOES_CONVERSIONS */
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2018, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,62 +20,28 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
#define ISLOWHEXALHA(x) (((x) >= 'a') && ((x) <= 'f'))
|
||||
#define ISUPHEXALHA(x) (((x) >= 'A') && ((x) <= 'F'))
|
||||
|
||||
#ifdef CURL_DOES_CONVERSIONS
|
||||
#define ISLOWCNTRL(x) ((unsigned char)(x) <= 0x1f)
|
||||
#define IS7F(x) ((x) == 0x7f)
|
||||
|
||||
/*
|
||||
* Uppercase macro versions of ANSI/ISO is*() functions/macros which
|
||||
* avoid negative number inputs with argument byte codes > 127.
|
||||
*
|
||||
* For non-ASCII platforms the C library character classification routines
|
||||
* are used despite being locale-dependent, because this is better than
|
||||
* not to work at all.
|
||||
*/
|
||||
#include <ctype.h>
|
||||
#define ISLOWPRINT(x) (((x) >= 9) && ((x) <= 0x0d))
|
||||
|
||||
#define ISSPACE(x) (isspace((int) ((unsigned char)x)))
|
||||
#define ISDIGIT(x) (isdigit((int) ((unsigned char)x)))
|
||||
#define ISALNUM(x) (isalnum((int) ((unsigned char)x)))
|
||||
#define ISXDIGIT(x) (isxdigit((int) ((unsigned char)x)))
|
||||
#define ISGRAPH(x) (isgraph((int) ((unsigned char)x)))
|
||||
#define ISALPHA(x) (isalpha((int) ((unsigned char)x)))
|
||||
#define ISPRINT(x) (isprint((int) ((unsigned char)x)))
|
||||
#define ISUPPER(x) (isupper((int) ((unsigned char)x)))
|
||||
#define ISLOWER(x) (islower((int) ((unsigned char)x)))
|
||||
#define ISCNTRL(x) (iscntrl((int) ((unsigned char)x)))
|
||||
#define ISASCII(x) (isascii((int) ((unsigned char)x)))
|
||||
|
||||
#else
|
||||
|
||||
int Curl_isspace(int c);
|
||||
int Curl_isdigit(int c);
|
||||
int Curl_isalnum(int c);
|
||||
int Curl_isxdigit(int c);
|
||||
int Curl_isgraph(int c);
|
||||
int Curl_isprint(int c);
|
||||
int Curl_isalpha(int c);
|
||||
int Curl_isupper(int c);
|
||||
int Curl_islower(int c);
|
||||
int Curl_iscntrl(int c);
|
||||
|
||||
#define ISSPACE(x) (Curl_isspace((int) ((unsigned char)x)))
|
||||
#define ISDIGIT(x) (Curl_isdigit((int) ((unsigned char)x)))
|
||||
#define ISALNUM(x) (Curl_isalnum((int) ((unsigned char)x)))
|
||||
#define ISXDIGIT(x) (Curl_isxdigit((int) ((unsigned char)x)))
|
||||
#define ISGRAPH(x) (Curl_isgraph((int) ((unsigned char)x)))
|
||||
#define ISALPHA(x) (Curl_isalpha((int) ((unsigned char)x)))
|
||||
#define ISPRINT(x) (Curl_isprint((int) ((unsigned char)x)))
|
||||
#define ISUPPER(x) (Curl_isupper((int) ((unsigned char)x)))
|
||||
#define ISLOWER(x) (Curl_islower((int) ((unsigned char)x)))
|
||||
#define ISCNTRL(x) (Curl_iscntrl((int) ((unsigned char)x)))
|
||||
#define ISASCII(x) (((x) >= 0) && ((x) <= 0x80))
|
||||
|
||||
#endif
|
||||
|
||||
#define ISBLANK(x) (int)((((unsigned char)x) == ' ') || \
|
||||
(((unsigned char)x) == '\t'))
|
||||
#define ISPRINT(x) (ISLOWPRINT(x) || (((x) >= ' ') && ((x) <= 0x7e)))
|
||||
#define ISGRAPH(x) (ISLOWPRINT(x) || (((x) > ' ') && ((x) <= 0x7e)))
|
||||
#define ISCNTRL(x) (ISLOWCNTRL(x) || IS7F(x))
|
||||
#define ISALPHA(x) (ISLOWER(x) || ISUPPER(x))
|
||||
#define ISXDIGIT(x) (ISDIGIT(x) || ISLOWHEXALHA(x) || ISUPHEXALHA(x))
|
||||
#define ISALNUM(x) (ISDIGIT(x) || ISLOWER(x) || ISUPPER(x))
|
||||
#define ISUPPER(x) (((x) >= 'A') && ((x) <= 'Z'))
|
||||
#define ISLOWER(x) (((x) >= 'a') && ((x) <= 'z'))
|
||||
#define ISDIGIT(x) (((x) >= '0') && ((x) <= '9'))
|
||||
#define ISBLANK(x) (((x) == ' ') || ((x) == '\t'))
|
||||
#define ISSPACE(x) (ISBLANK(x) || (((x) >= 0xa) && ((x) <= 0x0d)))
|
||||
|
||||
#endif /* HEADER_CURL_CTYPE_H */
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2015, Steve Holme, <steve_holme@hotmail.com>.
|
||||
* Copyright (C) Steve Holme, <steve_holme@hotmail.com>.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,11 +18,18 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if defined(USE_NTLM) && !defined(USE_OPENSSL)
|
||||
#if defined(USE_CURL_NTLM_CORE) && !defined(USE_WOLFSSL) && \
|
||||
(defined(USE_GNUTLS) || \
|
||||
defined(USE_NSS) || \
|
||||
defined(USE_SECTRANSP) || \
|
||||
defined(USE_OS400CRYPTO) || \
|
||||
defined(USE_WIN32_CRYPTO))
|
||||
|
||||
#include "curl_des.h"
|
||||
|
||||
|
@ -34,7 +41,7 @@
|
|||
*
|
||||
* The function is a port of the Java based oddParity() function over at:
|
||||
*
|
||||
* https://davenport.sourceforge.io/ntlm.html
|
||||
* https://davenport.sourceforge.net/ntlm.html
|
||||
*
|
||||
* Parameters:
|
||||
*
|
||||
|
@ -60,4 +67,4 @@ void Curl_des_set_odd_parity(unsigned char *bytes, size_t len)
|
|||
}
|
||||
}
|
||||
|
||||
#endif /* USE_NTLM && !USE_OPENSSL */
|
||||
#endif
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2015, Steve Holme, <steve_holme@hotmail.com>.
|
||||
* Copyright (C) Steve Holme, <steve_holme@hotmail.com>.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,15 +20,22 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if defined(USE_NTLM) && !defined(USE_OPENSSL)
|
||||
#if defined(USE_CURL_NTLM_CORE) && !defined(USE_WOLFSSL) && \
|
||||
(defined(USE_GNUTLS) || \
|
||||
defined(USE_NSS) || \
|
||||
defined(USE_SECTRANSP) || \
|
||||
defined(USE_OS400CRYPTO) || \
|
||||
defined(USE_WIN32_CRYPTO))
|
||||
|
||||
/* Applies odd parity to the given byte array */
|
||||
void Curl_des_set_odd_parity(unsigned char *bytes, size_t length);
|
||||
|
||||
#endif /* USE_NTLM && !USE_OPENSSL */
|
||||
#endif
|
||||
|
||||
#endif /* HEADER_CURL_DES_H */
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -80,45 +82,3 @@ unsigned short Curl_read16_be(const unsigned char *buf)
|
|||
return (unsigned short)(((unsigned short)buf[0] << 8) |
|
||||
((unsigned short)buf[1]));
|
||||
}
|
||||
|
||||
/*
|
||||
* write32_le()
|
||||
*
|
||||
* This function converts a 32-bit integer from the native endian format,
|
||||
* to little endian format ready for sending down the wire.
|
||||
*
|
||||
* Parameters:
|
||||
*
|
||||
* value [in] - The 32-bit integer value.
|
||||
* buffer [in] - A pointer to the output buffer.
|
||||
*/
|
||||
static void write32_le(const int value, unsigned char *buffer)
|
||||
{
|
||||
buffer[0] = (char)(value & 0x000000FF);
|
||||
buffer[1] = (char)((value & 0x0000FF00) >> 8);
|
||||
buffer[2] = (char)((value & 0x00FF0000) >> 16);
|
||||
buffer[3] = (char)((value & 0xFF000000) >> 24);
|
||||
}
|
||||
|
||||
#if (CURL_SIZEOF_CURL_OFF_T > 4)
|
||||
/*
|
||||
* Curl_write64_le()
|
||||
*
|
||||
* This function converts a 64-bit integer from the native endian format,
|
||||
* to little endian format ready for sending down the wire.
|
||||
*
|
||||
* Parameters:
|
||||
*
|
||||
* value [in] - The 64-bit integer value.
|
||||
* buffer [in] - A pointer to the output buffer.
|
||||
*/
|
||||
#if defined(HAVE_LONGLONG)
|
||||
void Curl_write64_le(const long long value, unsigned char *buffer)
|
||||
#else
|
||||
void Curl_write64_le(const __int64 value, unsigned char *buffer)
|
||||
#endif
|
||||
{
|
||||
write32_le((int)value, buffer);
|
||||
write32_le((int)(value >> 32), buffer + 4);
|
||||
}
|
||||
#endif /* CURL_SIZEOF_CURL_OFF_T > 4 */
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2017, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/* Converts a 16-bit integer from little endian */
|
||||
|
@ -31,16 +33,4 @@ unsigned int Curl_read32_le(const unsigned char *buf);
|
|||
/* Converts a 16-bit integer from big endian */
|
||||
unsigned short Curl_read16_be(const unsigned char *buf);
|
||||
|
||||
/* Converts a 32-bit integer to little endian */
|
||||
void Curl_write32_le(const int value, unsigned char *buffer);
|
||||
|
||||
#if (CURL_SIZEOF_CURL_OFF_T > 4)
|
||||
/* Converts a 64-bit integer to little endian */
|
||||
#if defined(HAVE_LONGLONG)
|
||||
void Curl_write64_le(const long long value, unsigned char *buffer);
|
||||
#else
|
||||
void Curl_write64_le(const __int64 value, unsigned char *buffer);
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#endif /* HEADER_CURL_ENDIAN_H */
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -74,9 +76,9 @@ static int parsekeyword(unsigned char **pattern, unsigned char *charset)
|
|||
parsekey_state state = CURLFNM_PKW_INIT;
|
||||
#define KEYLEN 10
|
||||
char keyword[KEYLEN] = { 0 };
|
||||
int found = FALSE;
|
||||
int i;
|
||||
unsigned char *p = *pattern;
|
||||
bool found = FALSE;
|
||||
for(i = 0; !found; i++) {
|
||||
char c = *p++;
|
||||
if(i >= KEYLEN)
|
||||
|
@ -366,14 +368,13 @@ int Curl_fnmatch(void *ptr, const char *pattern, const char *string)
|
|||
*/
|
||||
int Curl_fnmatch(void *ptr, const char *pattern, const char *string)
|
||||
{
|
||||
int rc;
|
||||
(void)ptr; /* the argument is specified by the curl_fnmatch_callback
|
||||
prototype, but not used by Curl_fnmatch() */
|
||||
if(!pattern || !string) {
|
||||
return CURL_FNMATCH_FAIL;
|
||||
}
|
||||
rc = fnmatch(pattern, string, 0);
|
||||
switch(rc) {
|
||||
|
||||
switch(fnmatch(pattern, string, 0)) {
|
||||
case 0:
|
||||
return CURL_FNMATCH_MATCH;
|
||||
case FNM_NOMATCH:
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2009, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#define CURL_FNMATCH_MATCH 0
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,38 +18,69 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if !defined(CURL_DISABLE_COOKIES) || !defined(CURL_DISABLE_ALTSVC) || \
|
||||
!defined(CURL_DISABLE_HSTS) || !defined(CURL_DISABLE_NETRC)
|
||||
|
||||
#include "curl_get_line.h"
|
||||
#include "curl_memory.h"
|
||||
/* The last #include file should be: */
|
||||
#include "memdebug.h"
|
||||
|
||||
/*
|
||||
* get_line() makes sure to only return complete whole lines that fit in 'len'
|
||||
* bytes and end with a newline.
|
||||
* Curl_get_line() makes sure to only return complete whole lines that fit in
|
||||
* 'len' bytes and end with a newline.
|
||||
*/
|
||||
char *Curl_get_line(char *buf, int len, FILE *input)
|
||||
{
|
||||
bool partial = FALSE;
|
||||
while(1) {
|
||||
char *b = fgets(buf, len, input);
|
||||
|
||||
if(b) {
|
||||
size_t rlen = strlen(b);
|
||||
if(rlen && (b[rlen-1] == '\n')) {
|
||||
|
||||
if(!rlen)
|
||||
break;
|
||||
|
||||
if(b[rlen-1] == '\n') {
|
||||
/* b is \n terminated */
|
||||
if(partial) {
|
||||
partial = FALSE;
|
||||
continue;
|
||||
}
|
||||
return b;
|
||||
}
|
||||
/* read a partial, discard the next piece that ends with newline */
|
||||
partial = TRUE;
|
||||
else if(feof(input)) {
|
||||
if(partial)
|
||||
/* Line is already too large to return, ignore rest */
|
||||
break;
|
||||
|
||||
if(rlen + 1 < (size_t) len) {
|
||||
/* b is EOF terminated, insert missing \n */
|
||||
b[rlen] = '\n';
|
||||
b[rlen + 1] = '\0';
|
||||
return b;
|
||||
}
|
||||
else
|
||||
/* Maximum buffersize reached + EOF
|
||||
* This line is impossible to add a \n to so we'll ignore it
|
||||
*/
|
||||
break;
|
||||
}
|
||||
else
|
||||
/* Maximum buffersize reached */
|
||||
partial = TRUE;
|
||||
}
|
||||
else
|
||||
break;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#endif /* if not disabled */
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/* get_line() makes sure to only return complete whole lines that fit in 'len'
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2016, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -48,7 +50,7 @@
|
|||
* For libcurl static library release builds no overriding takes place.
|
||||
*/
|
||||
|
||||
int Curl_gethostname(char *name, GETHOSTNAME_TYPE_ARG2 namelen)
|
||||
int Curl_gethostname(char * const name, GETHOSTNAME_TYPE_ARG2 namelen)
|
||||
{
|
||||
#ifndef HAVE_GETHOSTNAME
|
||||
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2010, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,12 +20,14 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/* Hostname buffer size */
|
||||
#define HOSTNAME_MAX 1024
|
||||
|
||||
/* This returns the local machine's un-qualified hostname */
|
||||
int Curl_gethostname(char *name, GETHOSTNAME_TYPE_ARG2 namelen);
|
||||
int Curl_gethostname(char * const name, GETHOSTNAME_TYPE_ARG2 namelen);
|
||||
|
||||
#endif /* HEADER_CURL_GETHOSTNAME_H */
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2011 - 2018, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
@ -32,10 +34,18 @@
|
|||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
static char spnego_oid_bytes[] = "\x2b\x06\x01\x05\x05\x02";
|
||||
gss_OID_desc Curl_spnego_mech_oid = { 6, &spnego_oid_bytes };
|
||||
static char krb5_oid_bytes[] = "\x2a\x86\x48\x86\xf7\x12\x01\x02\x02";
|
||||
gss_OID_desc Curl_krb5_mech_oid = { 9, &krb5_oid_bytes };
|
||||
#if defined(__GNUC__)
|
||||
#define CURL_ALIGN8 __attribute__ ((aligned(8)))
|
||||
#else
|
||||
#define CURL_ALIGN8
|
||||
#endif
|
||||
|
||||
gss_OID_desc Curl_spnego_mech_oid CURL_ALIGN8 = {
|
||||
6, (char *)"\x2b\x06\x01\x05\x05\x02"
|
||||
};
|
||||
gss_OID_desc Curl_krb5_mech_oid CURL_ALIGN8 = {
|
||||
9, (char *)"\x2a\x86\x48\x86\xf7\x12\x01\x02\x02"
|
||||
};
|
||||
|
||||
OM_uint32 Curl_gss_init_sec_context(
|
||||
struct Curl_easy *data,
|
||||
|
@ -58,8 +68,8 @@ OM_uint32 Curl_gss_init_sec_context(
|
|||
#ifdef GSS_C_DELEG_POLICY_FLAG
|
||||
req_flags |= GSS_C_DELEG_POLICY_FLAG;
|
||||
#else
|
||||
infof(data, "warning: support for CURLGSSAPI_DELEGATION_POLICY_FLAG not "
|
||||
"compiled in\n");
|
||||
infof(data, "WARNING: support for CURLGSSAPI_DELEGATION_POLICY_FLAG not "
|
||||
"compiled in");
|
||||
#endif
|
||||
}
|
||||
|
||||
|
@ -87,7 +97,7 @@ static size_t display_gss_error(OM_uint32 status, int type,
|
|||
OM_uint32 maj_stat;
|
||||
OM_uint32 min_stat;
|
||||
OM_uint32 msg_ctx = 0;
|
||||
gss_buffer_desc status_string;
|
||||
gss_buffer_desc status_string = GSS_C_EMPTY_BUFFER;
|
||||
|
||||
do {
|
||||
maj_stat = gss_display_status(&min_stat,
|
||||
|
@ -96,13 +106,15 @@ static size_t display_gss_error(OM_uint32 status, int type,
|
|||
GSS_C_NO_OID,
|
||||
&msg_ctx,
|
||||
&status_string);
|
||||
if(GSS_LOG_BUFFER_LEN > len + status_string.length + 3) {
|
||||
len += msnprintf(buf + len, GSS_LOG_BUFFER_LEN - len,
|
||||
"%.*s. ", (int)status_string.length,
|
||||
(char *)status_string.value);
|
||||
if(maj_stat == GSS_S_COMPLETE && status_string.length > 0) {
|
||||
if(GSS_LOG_BUFFER_LEN > len + status_string.length + 3) {
|
||||
len += msnprintf(buf + len, GSS_LOG_BUFFER_LEN - len,
|
||||
"%.*s. ", (int)status_string.length,
|
||||
(char *)status_string.value);
|
||||
}
|
||||
}
|
||||
gss_release_buffer(&min_stat, &status_string);
|
||||
} while(!GSS_ERROR(maj_stat) && msg_ctx != 0);
|
||||
} while(!GSS_ERROR(maj_stat) && msg_ctx);
|
||||
|
||||
return len;
|
||||
}
|
||||
|
@ -130,7 +142,11 @@ void Curl_gss_log_error(struct Curl_easy *data, const char *prefix,
|
|||
|
||||
display_gss_error(minor, GSS_C_MECH_CODE, buf, len);
|
||||
|
||||
infof(data, "%s%s\n", prefix, buf);
|
||||
infof(data, "%s%s", prefix, buf);
|
||||
#ifdef CURL_DISABLE_VERBOSE_STRINGS
|
||||
(void)data;
|
||||
(void)prefix;
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* HAVE_GSSAPI */
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 2011 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2016, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,11 +20,17 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#ifndef CURL_DISABLE_CRYPTO_AUTH
|
||||
|
||||
typedef void (* HMAC_hinit_func)(void *context);
|
||||
#include <curl/curl.h>
|
||||
|
||||
#define HMAC_MD5_LENGTH 16
|
||||
|
||||
typedef CURLcode (* HMAC_hinit_func)(void *context);
|
||||
typedef void (* HMAC_hupdate_func)(void *context,
|
||||
const unsigned char *data,
|
||||
unsigned int len);
|
||||
|
@ -32,35 +38,38 @@ typedef void (* HMAC_hfinal_func)(unsigned char *result, void *context);
|
|||
|
||||
|
||||
/* Per-hash function HMAC parameters. */
|
||||
|
||||
typedef struct {
|
||||
HMAC_hinit_func hmac_hinit; /* Initialize context procedure. */
|
||||
struct HMAC_params {
|
||||
HMAC_hinit_func
|
||||
hmac_hinit; /* Initialize context procedure. */
|
||||
HMAC_hupdate_func hmac_hupdate; /* Update context with data. */
|
||||
HMAC_hfinal_func hmac_hfinal; /* Get final result procedure. */
|
||||
unsigned int hmac_ctxtsize; /* Context structure size. */
|
||||
unsigned int hmac_maxkeylen; /* Maximum key length (bytes). */
|
||||
unsigned int hmac_resultlen; /* Result length (bytes). */
|
||||
} HMAC_params;
|
||||
};
|
||||
|
||||
|
||||
/* HMAC computation context. */
|
||||
|
||||
typedef struct {
|
||||
const HMAC_params *hmac_hash; /* Hash function definition. */
|
||||
struct HMAC_context {
|
||||
const struct HMAC_params *hmac_hash; /* Hash function definition. */
|
||||
void *hmac_hashctxt1; /* Hash function context 1. */
|
||||
void *hmac_hashctxt2; /* Hash function context 2. */
|
||||
} HMAC_context;
|
||||
};
|
||||
|
||||
|
||||
/* Prototypes. */
|
||||
|
||||
HMAC_context * Curl_HMAC_init(const HMAC_params *hashparams,
|
||||
const unsigned char *key,
|
||||
unsigned int keylen);
|
||||
int Curl_HMAC_update(HMAC_context *context,
|
||||
struct HMAC_context *Curl_HMAC_init(const struct HMAC_params *hashparams,
|
||||
const unsigned char *key,
|
||||
unsigned int keylen);
|
||||
int Curl_HMAC_update(struct HMAC_context *context,
|
||||
const unsigned char *data,
|
||||
unsigned int len);
|
||||
int Curl_HMAC_final(HMAC_context *context, unsigned char *result);
|
||||
int Curl_HMAC_final(struct HMAC_context *context, unsigned char *result);
|
||||
|
||||
CURLcode Curl_hmacit(const struct HMAC_params *hashparams,
|
||||
const unsigned char *key, const size_t keylen,
|
||||
const unsigned char *data, const size_t datalen,
|
||||
unsigned char *output);
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
#ifndef HEADER_CURL_SECURITY_H
|
||||
#define HEADER_CURL_SECURITY_H
|
||||
#ifndef HEADER_CURL_KRB5_H
|
||||
#define HEADER_CURL_KRB5_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2016, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,16 +20,17 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
struct Curl_sec_client_mech {
|
||||
const char *name;
|
||||
size_t size;
|
||||
int (*init)(void *);
|
||||
int (*auth)(void *, struct connectdata *);
|
||||
int (*auth)(void *, struct Curl_easy *data, struct connectdata *);
|
||||
void (*end)(void *);
|
||||
int (*check_prot)(void *, int);
|
||||
int (*overhead)(void *, int, int);
|
||||
int (*encode)(void *, const void *, int, int, void **);
|
||||
int (*decode)(void *, void *, int, int, struct connectdata *);
|
||||
};
|
||||
|
@ -39,13 +40,13 @@ struct Curl_sec_client_mech {
|
|||
#define AUTH_ERROR 2
|
||||
|
||||
#ifdef HAVE_GSSAPI
|
||||
int Curl_sec_read_msg(struct connectdata *conn, char *,
|
||||
int Curl_sec_read_msg(struct Curl_easy *data, struct connectdata *conn, char *,
|
||||
enum protection_level);
|
||||
void Curl_sec_end(struct connectdata *);
|
||||
CURLcode Curl_sec_login(struct connectdata *);
|
||||
CURLcode Curl_sec_login(struct Curl_easy *, struct connectdata *);
|
||||
int Curl_sec_request_prot(struct connectdata *conn, const char *level);
|
||||
|
||||
extern struct Curl_sec_client_mech Curl_krb5_client_mech;
|
||||
#else
|
||||
#define Curl_sec_end(x)
|
||||
#endif
|
||||
|
||||
#endif /* HEADER_CURL_SECURITY_H */
|
||||
#endif /* HEADER_CURL_KRB5_H */
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2010, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#ifndef CURL_DISABLE_LDAP
|
||||
extern const struct Curl_handler Curl_handler_ldap;
|
||||
|
|
223
src/dependencies/cmcurl/lib/curl_log.c
Normal file
223
src/dependencies/cmcurl/lib/curl_log.c
Normal file
|
@ -0,0 +1,223 @@
|
|||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#include <curl/curl.h>
|
||||
|
||||
#include "curl_log.h"
|
||||
#include "urldata.h"
|
||||
#include "easyif.h"
|
||||
#include "cfilters.h"
|
||||
#include "timeval.h"
|
||||
#include "multiif.h"
|
||||
#include "strcase.h"
|
||||
|
||||
#include "cf-socket.h"
|
||||
#include "connect.h"
|
||||
#include "http2.h"
|
||||
#include "http_proxy.h"
|
||||
#include "cf-https-connect.h"
|
||||
#include "socks.h"
|
||||
#include "strtok.h"
|
||||
#include "vtls/vtls.h"
|
||||
#include "vquic/vquic.h"
|
||||
|
||||
/* The last 3 #include files should be in this order */
|
||||
#include "curl_printf.h"
|
||||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
|
||||
void Curl_debug(struct Curl_easy *data, curl_infotype type,
|
||||
char *ptr, size_t size)
|
||||
{
|
||||
if(data->set.verbose) {
|
||||
static const char s_infotype[CURLINFO_END][3] = {
|
||||
"* ", "< ", "> ", "{ ", "} ", "{ ", "} " };
|
||||
if(data->set.fdebug) {
|
||||
bool inCallback = Curl_is_in_callback(data);
|
||||
Curl_set_in_callback(data, true);
|
||||
(void)(*data->set.fdebug)(data, type, ptr, size, data->set.debugdata);
|
||||
Curl_set_in_callback(data, inCallback);
|
||||
}
|
||||
else {
|
||||
switch(type) {
|
||||
case CURLINFO_TEXT:
|
||||
case CURLINFO_HEADER_OUT:
|
||||
case CURLINFO_HEADER_IN:
|
||||
fwrite(s_infotype[type], 2, 1, data->set.err);
|
||||
fwrite(ptr, size, 1, data->set.err);
|
||||
break;
|
||||
default: /* nada */
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* Curl_failf() is for messages stating why we failed.
|
||||
* The message SHALL NOT include any LF or CR.
|
||||
*/
|
||||
void Curl_failf(struct Curl_easy *data, const char *fmt, ...)
|
||||
{
|
||||
DEBUGASSERT(!strchr(fmt, '\n'));
|
||||
if(data->set.verbose || data->set.errorbuffer) {
|
||||
va_list ap;
|
||||
int len;
|
||||
char error[CURL_ERROR_SIZE + 2];
|
||||
va_start(ap, fmt);
|
||||
len = mvsnprintf(error, CURL_ERROR_SIZE, fmt, ap);
|
||||
|
||||
if(data->set.errorbuffer && !data->state.errorbuf) {
|
||||
strcpy(data->set.errorbuffer, error);
|
||||
data->state.errorbuf = TRUE; /* wrote error string */
|
||||
}
|
||||
error[len++] = '\n';
|
||||
error[len] = '\0';
|
||||
Curl_debug(data, CURLINFO_TEXT, error, len);
|
||||
va_end(ap);
|
||||
}
|
||||
}
|
||||
|
||||
/* Curl_infof() is for info message along the way */
|
||||
#define MAXINFO 2048
|
||||
|
||||
void Curl_infof(struct Curl_easy *data, const char *fmt, ...)
|
||||
{
|
||||
DEBUGASSERT(!strchr(fmt, '\n'));
|
||||
if(data && data->set.verbose) {
|
||||
va_list ap;
|
||||
int len;
|
||||
char buffer[MAXINFO + 2];
|
||||
va_start(ap, fmt);
|
||||
len = mvsnprintf(buffer, MAXINFO, fmt, ap);
|
||||
va_end(ap);
|
||||
buffer[len++] = '\n';
|
||||
buffer[len] = '\0';
|
||||
Curl_debug(data, CURLINFO_TEXT, buffer, len);
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef DEBUGBUILD
|
||||
|
||||
void Curl_log_cf_debug(struct Curl_easy *data, struct Curl_cfilter *cf,
|
||||
const char *fmt, ...)
|
||||
{
|
||||
DEBUGASSERT(cf);
|
||||
if(data && Curl_log_cf_is_debug(cf)) {
|
||||
va_list ap;
|
||||
int len;
|
||||
char buffer[MAXINFO + 2];
|
||||
len = msnprintf(buffer, MAXINFO, "[CONN-%ld%s-%s] ",
|
||||
cf->conn->connection_id, cf->sockindex? "/2" : "",
|
||||
cf->cft->name);
|
||||
va_start(ap, fmt);
|
||||
len += mvsnprintf(buffer + len, MAXINFO - len, fmt, ap);
|
||||
va_end(ap);
|
||||
buffer[len++] = '\n';
|
||||
buffer[len] = '\0';
|
||||
Curl_debug(data, CURLINFO_TEXT, buffer, len);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static struct Curl_cftype *cf_types[] = {
|
||||
&Curl_cft_tcp,
|
||||
&Curl_cft_udp,
|
||||
&Curl_cft_unix,
|
||||
&Curl_cft_tcp_accept,
|
||||
&Curl_cft_happy_eyeballs,
|
||||
&Curl_cft_setup,
|
||||
#ifdef USE_NGHTTP2
|
||||
&Curl_cft_nghttp2,
|
||||
#endif
|
||||
#ifdef USE_SSL
|
||||
&Curl_cft_ssl,
|
||||
&Curl_cft_ssl_proxy,
|
||||
#endif
|
||||
#if !defined(CURL_DISABLE_PROXY)
|
||||
#if !defined(CURL_DISABLE_HTTP)
|
||||
&Curl_cft_http_proxy,
|
||||
#endif /* !CURL_DISABLE_HTTP */
|
||||
&Curl_cft_haproxy,
|
||||
&Curl_cft_socks_proxy,
|
||||
#endif /* !CURL_DISABLE_PROXY */
|
||||
#ifdef ENABLE_QUIC
|
||||
&Curl_cft_http3,
|
||||
#endif
|
||||
#if !defined(CURL_DISABLE_HTTP) && !defined(USE_HYPER)
|
||||
&Curl_cft_http_connect,
|
||||
#endif
|
||||
NULL,
|
||||
};
|
||||
|
||||
#ifndef ARRAYSIZE
|
||||
#define ARRAYSIZE(A) (sizeof(A)/sizeof((A)[0]))
|
||||
#endif
|
||||
|
||||
CURLcode Curl_log_init(void)
|
||||
{
|
||||
const char *setting = getenv("CURL_DEBUG");
|
||||
if(setting) {
|
||||
char *token, *tok_buf, *tmp;
|
||||
size_t i;
|
||||
|
||||
tmp = strdup(setting);
|
||||
if(!tmp)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
||||
token = strtok_r(tmp, ", ", &tok_buf);
|
||||
while(token) {
|
||||
for(i = 0; cf_types[i]; ++i) {
|
||||
if(strcasecompare(token, cf_types[i]->name)) {
|
||||
cf_types[i]->log_level = CURL_LOG_DEBUG;
|
||||
break;
|
||||
}
|
||||
}
|
||||
token = strtok_r(NULL, ", ", &tok_buf);
|
||||
}
|
||||
free(tmp);
|
||||
}
|
||||
return CURLE_OK;
|
||||
}
|
||||
#else /* DEBUGBUILD */
|
||||
|
||||
CURLcode Curl_log_init(void)
|
||||
{
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
#if !defined(__STDC_VERSION__) || (__STDC_VERSION__ < 199901L)
|
||||
void Curl_log_cf_debug(struct Curl_easy *data, struct Curl_cfilter *cf,
|
||||
const char *fmt, ...)
|
||||
{
|
||||
(void)data;
|
||||
(void)cf;
|
||||
(void)fmt;
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* !DEBUGBUILD */
|
138
src/dependencies/cmcurl/lib/curl_log.h
Normal file
138
src/dependencies/cmcurl/lib/curl_log.h
Normal file
|
@ -0,0 +1,138 @@
|
|||
#ifndef HEADER_CURL_LOG_H
|
||||
#define HEADER_CURL_LOG_H
|
||||
/***************************************************************************
|
||||
* _ _ ____ _
|
||||
* Project ___| | | | _ \| |
|
||||
* / __| | | | |_) | |
|
||||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
* furnished to do so, under the terms of the COPYING file.
|
||||
*
|
||||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
struct Curl_easy;
|
||||
struct Curl_cfilter;
|
||||
|
||||
/**
|
||||
* Init logging, return != 0 on failure.
|
||||
*/
|
||||
CURLcode Curl_log_init(void);
|
||||
|
||||
|
||||
void Curl_infof(struct Curl_easy *, const char *fmt, ...);
|
||||
void Curl_failf(struct Curl_easy *, const char *fmt, ...);
|
||||
|
||||
#if defined(CURL_DISABLE_VERBOSE_STRINGS)
|
||||
|
||||
#if defined(HAVE_VARIADIC_MACROS_C99)
|
||||
#define infof(...) Curl_nop_stmt
|
||||
#elif defined(HAVE_VARIADIC_MACROS_GCC)
|
||||
#define infof(x...) Curl_nop_stmt
|
||||
#else
|
||||
#error "missing VARIADIC macro define, fix and rebuild!"
|
||||
#endif
|
||||
|
||||
#else /* CURL_DISABLE_VERBOSE_STRINGS */
|
||||
|
||||
#define infof Curl_infof
|
||||
|
||||
#endif /* CURL_DISABLE_VERBOSE_STRINGS */
|
||||
|
||||
#define failf Curl_failf
|
||||
|
||||
|
||||
#define CURL_LOG_DEFAULT 0
|
||||
#define CURL_LOG_DEBUG 1
|
||||
#define CURL_LOG_TRACE 2
|
||||
|
||||
|
||||
/* the function used to output verbose information */
|
||||
void Curl_debug(struct Curl_easy *data, curl_infotype type,
|
||||
char *ptr, size_t size);
|
||||
|
||||
#ifdef DEBUGBUILD
|
||||
|
||||
/* explainer: we have some mix configuration and werror settings
|
||||
* that define HAVE_VARIADIC_MACROS_C99 even though C89 is enforced
|
||||
* on gnuc and some other compiler. Need to treat carefully.
|
||||
*/
|
||||
#if defined(HAVE_VARIADIC_MACROS_C99) && \
|
||||
defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L)
|
||||
|
||||
#define LOG_CF(data, cf, ...) \
|
||||
do { if(Curl_log_cf_is_debug(cf)) \
|
||||
Curl_log_cf_debug(data, cf, __VA_ARGS__); } while(0)
|
||||
#else
|
||||
#define LOG_CF Curl_log_cf_debug
|
||||
#endif
|
||||
|
||||
void Curl_log_cf_debug(struct Curl_easy *data, struct Curl_cfilter *cf,
|
||||
#if defined(__GNUC__) && !defined(printf) && \
|
||||
defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) && \
|
||||
!defined(__MINGW32__)
|
||||
const char *fmt, ...)
|
||||
__attribute__((format(printf, 3, 4)));
|
||||
#else
|
||||
const char *fmt, ...);
|
||||
#endif
|
||||
|
||||
#define Curl_log_cf_is_debug(cf) \
|
||||
((cf) && (cf)->cft->log_level >= CURL_LOG_DEBUG)
|
||||
|
||||
#else /* !DEBUGBUILD */
|
||||
|
||||
#if defined(HAVE_VARIADIC_MACROS_C99) && \
|
||||
defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L)
|
||||
#define LOG_CF(...) Curl_nop_stmt
|
||||
#define Curl_log_cf_debug(...) Curl_nop_stmt
|
||||
#elif defined(HAVE_VARIADIC_MACROS_GCC) && \
|
||||
defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L)
|
||||
#define LOG_CF(x...) Curl_nop_stmt
|
||||
#define Curl_log_cf_debug(x...) Curl_nop_stmt
|
||||
#else
|
||||
#define LOG_CF Curl_log_cf_debug
|
||||
/* without c99, we seem unable to completely define away this function. */
|
||||
void Curl_log_cf_debug(struct Curl_easy *data, struct Curl_cfilter *cf,
|
||||
const char *fmt, ...);
|
||||
#endif
|
||||
|
||||
#define Curl_log_cf_is_debug(x) ((void)(x), FALSE)
|
||||
|
||||
#endif /* !DEBUGBUILD */
|
||||
|
||||
#define LOG_CF_IS_DEBUG(x) Curl_log_cf_is_debug(x)
|
||||
|
||||
/* Macros intended for DEBUGF logging, use like:
|
||||
* DEBUGF(infof(data, CFMSG(cf, "this filter %s rocks"), "very much"));
|
||||
* and it will output:
|
||||
* [CONN-1-0][CF-SSL] this filter very much rocks
|
||||
* on connection #1 with sockindex 0 for filter of type "SSL". */
|
||||
#define DMSG(d,msg) \
|
||||
"[CONN-%ld] "msg, (d)->conn->connection_id
|
||||
#define DMSGI(d,i,msg) \
|
||||
"[CONN-%ld-%d] "msg, (d)->conn->connection_id, (i)
|
||||
#define CMSG(c,msg) \
|
||||
"[CONN-%ld] "msg, (c)->connection_id
|
||||
#define CMSGI(c,i,msg) \
|
||||
"[CONN-%ld-%d] "msg, (c)->connection_id, (i)
|
||||
#define CFMSG(cf,msg) \
|
||||
"[CONN-%ld-%d][CF-%s] "msg, (cf)->conn->connection_id, \
|
||||
(cf)->sockindex, (cf)->cft->name
|
||||
|
||||
|
||||
|
||||
#endif /* HEADER_CURL_LOG_H */
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,18 +20,19 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if defined(USE_NSS) || defined(USE_OS400CRYPTO) || \
|
||||
(defined(USE_OPENSSL) && defined(OPENSSL_NO_MD4)) || \
|
||||
(defined(USE_MBEDTLS) && !defined(MBEDTLS_MD4_C))
|
||||
#if !defined(CURL_DISABLE_CRYPTO_AUTH)
|
||||
|
||||
void Curl_md4it(unsigned char *output, const unsigned char *input, size_t len);
|
||||
#define MD4_DIGEST_LENGTH 16
|
||||
|
||||
#endif /* defined(USE_NSS) || defined(USE_OS400CRYPTO) ||
|
||||
(defined(USE_OPENSSL) && defined(OPENSSL_NO_MD4)) ||
|
||||
(defined(USE_MBEDTLS) && !defined(MBEDTLS_MD4_C)) */
|
||||
void Curl_md4it(unsigned char *output, const unsigned char *input,
|
||||
const size_t len);
|
||||
|
||||
#endif /* !defined(CURL_DISABLE_CRYPTO_AUTH) */
|
||||
|
||||
#endif /* HEADER_CURL_MD4_H */
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#ifndef CURL_DISABLE_CRYPTO_AUTH
|
||||
|
@ -27,36 +29,36 @@
|
|||
|
||||
#define MD5_DIGEST_LEN 16
|
||||
|
||||
typedef void (* Curl_MD5_init_func)(void *context);
|
||||
typedef CURLcode (* Curl_MD5_init_func)(void *context);
|
||||
typedef void (* Curl_MD5_update_func)(void *context,
|
||||
const unsigned char *data,
|
||||
unsigned int len);
|
||||
typedef void (* Curl_MD5_final_func)(unsigned char *result, void *context);
|
||||
|
||||
typedef struct {
|
||||
struct MD5_params {
|
||||
Curl_MD5_init_func md5_init_func; /* Initialize context procedure */
|
||||
Curl_MD5_update_func md5_update_func; /* Update context with data */
|
||||
Curl_MD5_final_func md5_final_func; /* Get final result procedure */
|
||||
unsigned int md5_ctxtsize; /* Context structure size */
|
||||
unsigned int md5_resultlen; /* Result length (bytes) */
|
||||
} MD5_params;
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
const MD5_params *md5_hash; /* Hash function definition */
|
||||
struct MD5_context {
|
||||
const struct MD5_params *md5_hash; /* Hash function definition */
|
||||
void *md5_hashctx; /* Hash function context */
|
||||
} MD5_context;
|
||||
};
|
||||
|
||||
extern const MD5_params Curl_DIGEST_MD5[1];
|
||||
extern const HMAC_params Curl_HMAC_MD5[1];
|
||||
extern const struct MD5_params Curl_DIGEST_MD5[1];
|
||||
extern const struct HMAC_params Curl_HMAC_MD5[1];
|
||||
|
||||
void Curl_md5it(unsigned char *output,
|
||||
const unsigned char *input);
|
||||
CURLcode Curl_md5it(unsigned char *output, const unsigned char *input,
|
||||
const size_t len);
|
||||
|
||||
MD5_context * Curl_MD5_init(const MD5_params *md5params);
|
||||
CURLcode Curl_MD5_update(MD5_context *context,
|
||||
struct MD5_context *Curl_MD5_init(const struct MD5_params *md5params);
|
||||
CURLcode Curl_MD5_update(struct MD5_context *context,
|
||||
const unsigned char *data,
|
||||
unsigned int len);
|
||||
CURLcode Curl_MD5_final(MD5_context *context, unsigned char *result);
|
||||
CURLcode Curl_MD5_final(struct MD5_context *context, unsigned char *result);
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/*
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2018, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,6 +18,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2009, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,6 +20,8 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2015, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,26 +18,29 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
/*
|
||||
* This file is 'mem-include-scan' clean, which means memdebug.h and
|
||||
* curl_memory.h are purposely not included in this file. See test 1132.
|
||||
*
|
||||
* The functions in this file are curlx functions which are not tracked by the
|
||||
* curl memory tracker memdebug.
|
||||
*/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#include <curl/curl.h>
|
||||
|
||||
#if defined(USE_WIN32_IDN) || ((defined(USE_WINDOWS_SSPI) || \
|
||||
defined(USE_WIN32_LDAP)) && defined(UNICODE))
|
||||
|
||||
/*
|
||||
* MultiByte conversions using Windows kernel32 library.
|
||||
*/
|
||||
#if defined(WIN32)
|
||||
|
||||
#include "curl_multibyte.h"
|
||||
#include "curl_memory.h"
|
||||
|
||||
/* The last #include file should be: */
|
||||
#include "memdebug.h"
|
||||
/*
|
||||
* MultiByte conversions using Windows kernel32 library.
|
||||
*/
|
||||
|
||||
wchar_t *Curl_convert_UTF8_to_wchar(const char *str_utf8)
|
||||
wchar_t *curlx_convert_UTF8_to_wchar(const char *str_utf8)
|
||||
{
|
||||
wchar_t *str_w = NULL;
|
||||
|
||||
|
@ -59,7 +62,7 @@ wchar_t *Curl_convert_UTF8_to_wchar(const char *str_utf8)
|
|||
return str_w;
|
||||
}
|
||||
|
||||
char *Curl_convert_wchar_to_UTF8(const wchar_t *str_w)
|
||||
char *curlx_convert_wchar_to_UTF8(const wchar_t *str_w)
|
||||
{
|
||||
char *str_utf8 = NULL;
|
||||
|
||||
|
@ -81,4 +84,96 @@ char *Curl_convert_wchar_to_UTF8(const wchar_t *str_w)
|
|||
return str_utf8;
|
||||
}
|
||||
|
||||
#endif /* USE_WIN32_IDN || ((USE_WINDOWS_SSPI || USE_WIN32_LDAP) && UNICODE) */
|
||||
#endif /* WIN32 */
|
||||
|
||||
#if defined(USE_WIN32_LARGE_FILES) || defined(USE_WIN32_SMALL_FILES)
|
||||
|
||||
int curlx_win32_open(const char *filename, int oflag, ...)
|
||||
{
|
||||
int pmode = 0;
|
||||
|
||||
#ifdef _UNICODE
|
||||
int result = -1;
|
||||
wchar_t *filename_w = curlx_convert_UTF8_to_wchar(filename);
|
||||
#endif
|
||||
|
||||
va_list param;
|
||||
va_start(param, oflag);
|
||||
if(oflag & O_CREAT)
|
||||
pmode = va_arg(param, int);
|
||||
va_end(param);
|
||||
|
||||
#ifdef _UNICODE
|
||||
if(filename_w) {
|
||||
result = _wopen(filename_w, oflag, pmode);
|
||||
curlx_unicodefree(filename_w);
|
||||
}
|
||||
else
|
||||
errno = EINVAL;
|
||||
return result;
|
||||
#else
|
||||
return (_open)(filename, oflag, pmode);
|
||||
#endif
|
||||
}
|
||||
|
||||
FILE *curlx_win32_fopen(const char *filename, const char *mode)
|
||||
{
|
||||
#ifdef _UNICODE
|
||||
FILE *result = NULL;
|
||||
wchar_t *filename_w = curlx_convert_UTF8_to_wchar(filename);
|
||||
wchar_t *mode_w = curlx_convert_UTF8_to_wchar(mode);
|
||||
if(filename_w && mode_w)
|
||||
result = _wfopen(filename_w, mode_w);
|
||||
else
|
||||
errno = EINVAL;
|
||||
curlx_unicodefree(filename_w);
|
||||
curlx_unicodefree(mode_w);
|
||||
return result;
|
||||
#else
|
||||
return (fopen)(filename, mode);
|
||||
#endif
|
||||
}
|
||||
|
||||
int curlx_win32_stat(const char *path, struct_stat *buffer)
|
||||
{
|
||||
#ifdef _UNICODE
|
||||
int result = -1;
|
||||
wchar_t *path_w = curlx_convert_UTF8_to_wchar(path);
|
||||
if(path_w) {
|
||||
#if defined(USE_WIN32_SMALL_FILES)
|
||||
result = _wstat(path_w, buffer);
|
||||
#else
|
||||
result = _wstati64(path_w, buffer);
|
||||
#endif
|
||||
curlx_unicodefree(path_w);
|
||||
}
|
||||
else
|
||||
errno = EINVAL;
|
||||
return result;
|
||||
#else
|
||||
#if defined(USE_WIN32_SMALL_FILES)
|
||||
return _stat(path, buffer);
|
||||
#else
|
||||
return _stati64(path, buffer);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
|
||||
int curlx_win32_access(const char *path, int mode)
|
||||
{
|
||||
#if defined(_UNICODE)
|
||||
int result = -1;
|
||||
wchar_t *path_w = curlx_convert_UTF8_to_wchar(path);
|
||||
if(path_w) {
|
||||
result = _waccess(path_w, mode);
|
||||
curlx_unicodefree(path_w);
|
||||
}
|
||||
else
|
||||
errno = EINVAL;
|
||||
return result;
|
||||
#else
|
||||
return _access(path, mode);
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* USE_WIN32_LARGE_FILES || USE_WIN32_SMALL_FILES */
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2015, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,49 +20,44 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if defined(USE_WIN32_IDN) || ((defined(USE_WINDOWS_SSPI) || \
|
||||
defined(USE_WIN32_LDAP)) && defined(UNICODE))
|
||||
#if defined(WIN32)
|
||||
|
||||
/*
|
||||
* MultiByte conversions using Windows kernel32 library.
|
||||
*/
|
||||
|
||||
wchar_t *Curl_convert_UTF8_to_wchar(const char *str_utf8);
|
||||
char *Curl_convert_wchar_to_UTF8(const wchar_t *str_w);
|
||||
|
||||
#endif /* USE_WIN32_IDN || ((USE_WINDOWS_SSPI || USE_WIN32_LDAP) && UNICODE) */
|
||||
|
||||
|
||||
#if defined(USE_WIN32_IDN) || defined(USE_WINDOWS_SSPI) || \
|
||||
defined(USE_WIN32_LDAP)
|
||||
wchar_t *curlx_convert_UTF8_to_wchar(const char *str_utf8);
|
||||
char *curlx_convert_wchar_to_UTF8(const wchar_t *str_w);
|
||||
#endif /* WIN32 */
|
||||
|
||||
/*
|
||||
* Macros Curl_convert_UTF8_to_tchar(), Curl_convert_tchar_to_UTF8()
|
||||
* and Curl_unicodefree() main purpose is to minimize the number of
|
||||
* Macros curlx_convert_UTF8_to_tchar(), curlx_convert_tchar_to_UTF8()
|
||||
* and curlx_unicodefree() main purpose is to minimize the number of
|
||||
* preprocessor conditional directives needed by code using these
|
||||
* to differentiate UNICODE from non-UNICODE builds.
|
||||
*
|
||||
* When building with UNICODE defined, this two macros
|
||||
* Curl_convert_UTF8_to_tchar() and Curl_convert_tchar_to_UTF8()
|
||||
* return a pointer to a newly allocated memory area holding result.
|
||||
* When the result is no longer needed, allocated memory is intended
|
||||
* to be free'ed with Curl_unicodefree().
|
||||
* In the case of a non-UNICODE build the tchar strings are char strings that
|
||||
* are duplicated via strdup and remain in whatever the passed in encoding is,
|
||||
* which is assumed to be UTF-8 but may be other encoding. Therefore the
|
||||
* significance of the conversion functions is primarily for UNICODE builds.
|
||||
*
|
||||
* When building without UNICODE defined, this macros
|
||||
* Curl_convert_UTF8_to_tchar() and Curl_convert_tchar_to_UTF8()
|
||||
* return the pointer received as argument. Curl_unicodefree() does
|
||||
* no actual free'ing of this pointer it is simply set to NULL.
|
||||
* Allocated memory should be free'd with curlx_unicodefree().
|
||||
*
|
||||
* Note: Because these are curlx functions their memory usage is not tracked
|
||||
* by the curl memory tracker memdebug. You'll notice that curlx function-like
|
||||
* macros call free and strdup in parentheses, eg (strdup)(ptr), and that's to
|
||||
* ensure that the curl memdebug override macros do not replace them.
|
||||
*/
|
||||
|
||||
#ifdef UNICODE
|
||||
#if defined(UNICODE) && defined(WIN32)
|
||||
|
||||
#define Curl_convert_UTF8_to_tchar(ptr) Curl_convert_UTF8_to_wchar((ptr))
|
||||
#define Curl_convert_tchar_to_UTF8(ptr) Curl_convert_wchar_to_UTF8((ptr))
|
||||
#define Curl_unicodefree(ptr) \
|
||||
do {if((ptr)) {free((ptr)); (ptr) = NULL;}} WHILE_FALSE
|
||||
#define curlx_convert_UTF8_to_tchar(ptr) curlx_convert_UTF8_to_wchar((ptr))
|
||||
#define curlx_convert_tchar_to_UTF8(ptr) curlx_convert_wchar_to_UTF8((ptr))
|
||||
|
||||
typedef union {
|
||||
unsigned short *tchar_ptr;
|
||||
|
@ -73,10 +68,8 @@ typedef union {
|
|||
|
||||
#else
|
||||
|
||||
#define Curl_convert_UTF8_to_tchar(ptr) (ptr)
|
||||
#define Curl_convert_tchar_to_UTF8(ptr) (ptr)
|
||||
#define Curl_unicodefree(ptr) \
|
||||
do {(ptr) = NULL;} WHILE_FALSE
|
||||
#define curlx_convert_UTF8_to_tchar(ptr) (strdup)(ptr)
|
||||
#define curlx_convert_tchar_to_UTF8(ptr) (strdup)(ptr)
|
||||
|
||||
typedef union {
|
||||
char *tchar_ptr;
|
||||
|
@ -85,8 +78,14 @@ typedef union {
|
|||
const unsigned char *const_tbyte_ptr;
|
||||
} xcharp_u;
|
||||
|
||||
#endif /* UNICODE */
|
||||
#endif /* UNICODE && WIN32 */
|
||||
|
||||
#endif /* USE_WIN32_IDN || USE_WINDOWS_SSPI || USE_WIN32_LDAP */
|
||||
#define curlx_unicodefree(ptr) \
|
||||
do { \
|
||||
if(ptr) { \
|
||||
(free)(ptr); \
|
||||
(ptr) = NULL; \
|
||||
} \
|
||||
} while(0)
|
||||
|
||||
#endif /* HEADER_CURL_MULTIBYTE_H */
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -18,23 +18,25 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if defined(USE_NTLM)
|
||||
#if defined(USE_CURL_NTLM_CORE)
|
||||
|
||||
/*
|
||||
* NTLM details:
|
||||
*
|
||||
* https://davenport.sourceforge.io/ntlm.html
|
||||
* https://davenport.sourceforge.net/ntlm.html
|
||||
* https://www.innovation.ch/java/ntlm.html
|
||||
*/
|
||||
|
||||
/* Please keep the SSL backend-specific #if branches in this order:
|
||||
|
||||
1. USE_OPENSSL
|
||||
2. USE_GNUTLS_NETTLE
|
||||
2. USE_WOLFSSL
|
||||
3. USE_GNUTLS
|
||||
4. USE_NSS
|
||||
5. USE_MBEDTLS
|
||||
|
@ -50,20 +52,30 @@
|
|||
in NTLM type-3 messages.
|
||||
*/
|
||||
|
||||
#if !defined(USE_WINDOWS_SSPI) || defined(USE_WIN32_CRYPTO)
|
||||
#if defined(USE_OPENSSL)
|
||||
#include <openssl/opensslconf.h>
|
||||
#if !defined(OPENSSL_NO_DES) && !defined(OPENSSL_NO_DEPRECATED_3_0)
|
||||
#define USE_OPENSSL_DES
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef USE_OPENSSL
|
||||
#if defined(USE_OPENSSL_DES) || defined(USE_WOLFSSL)
|
||||
|
||||
#if defined(USE_OPENSSL)
|
||||
# include <openssl/des.h>
|
||||
# ifndef OPENSSL_NO_MD4
|
||||
# include <openssl/md4.h>
|
||||
# else
|
||||
# include "curl_md4.h"
|
||||
# endif
|
||||
# include <openssl/md5.h>
|
||||
# include <openssl/ssl.h>
|
||||
# include <openssl/rand.h>
|
||||
# if (OPENSSL_VERSION_NUMBER < 0x00907001L)
|
||||
#else
|
||||
# include <wolfssl/options.h>
|
||||
# include <wolfssl/openssl/des.h>
|
||||
# include <wolfssl/openssl/md5.h>
|
||||
# include <wolfssl/openssl/ssl.h>
|
||||
# include <wolfssl/openssl/rand.h>
|
||||
#endif
|
||||
|
||||
# if (defined(OPENSSL_VERSION_NUMBER) && \
|
||||
(OPENSSL_VERSION_NUMBER < 0x00907001L)) && !defined(USE_WOLFSSL)
|
||||
# define DES_key_schedule des_key_schedule
|
||||
# define DES_cblock des_cblock
|
||||
# define DES_set_odd_parity des_set_odd_parity
|
||||
|
@ -76,32 +88,19 @@
|
|||
# define DESKEY(x) &x
|
||||
# endif
|
||||
|
||||
#elif defined(USE_GNUTLS_NETTLE)
|
||||
|
||||
# include <nettle/des.h>
|
||||
# include <nettle/md4.h>
|
||||
|
||||
#elif defined(USE_GNUTLS)
|
||||
|
||||
# include <gcrypt.h>
|
||||
# define MD5_DIGEST_LENGTH 16
|
||||
# define MD4_DIGEST_LENGTH 16
|
||||
# include <nettle/des.h>
|
||||
|
||||
#elif defined(USE_NSS)
|
||||
|
||||
# include <nss.h>
|
||||
# include <pk11pub.h>
|
||||
# include <hasht.h>
|
||||
# include "curl_md4.h"
|
||||
# define MD5_DIGEST_LENGTH MD5_LENGTH
|
||||
|
||||
#elif defined(USE_MBEDTLS)
|
||||
|
||||
# include <mbedtls/des.h>
|
||||
# include <mbedtls/md4.h>
|
||||
# if !defined(MBEDTLS_MD4_C)
|
||||
# include "curl_md4.h"
|
||||
# endif
|
||||
|
||||
#elif defined(USE_SECTRANSP)
|
||||
|
||||
|
@ -110,15 +109,13 @@
|
|||
|
||||
#elif defined(USE_OS400CRYPTO)
|
||||
# include "cipher.mih" /* mih/cipher */
|
||||
# include "curl_md4.h"
|
||||
#elif defined(USE_WIN32_CRYPTO)
|
||||
# include <wincrypt.h>
|
||||
#else
|
||||
# error "Can't compile NTLM support without a crypto library."
|
||||
# error "Can't compile NTLM support without a crypto library with DES."
|
||||
#endif
|
||||
|
||||
#include "urldata.h"
|
||||
#include "non-ascii.h"
|
||||
#include "strcase.h"
|
||||
#include "curl_ntlm_core.h"
|
||||
#include "curl_md5.h"
|
||||
|
@ -126,12 +123,12 @@
|
|||
#include "warnless.h"
|
||||
#include "curl_endian.h"
|
||||
#include "curl_des.h"
|
||||
#include "curl_md4.h"
|
||||
/* The last 3 #include files should be in this order */
|
||||
#include "curl_printf.h"
|
||||
#include "curl_memory.h"
|
||||
#include "memdebug.h"
|
||||
|
||||
#define NTLM_HMAC_MD5_LEN (16)
|
||||
#define NTLMv2_BLOB_SIGNATURE "\x01\x01\x00\x00"
|
||||
#define NTLMv2_BLOB_LEN (44 -16 + ntlm->target_info_len + 4)
|
||||
|
||||
|
@ -150,7 +147,7 @@ static void extend_key_56_to_64(const unsigned char *key_56, char *key)
|
|||
key[7] = (unsigned char) ((key_56[6] << 1) & 0xFF);
|
||||
}
|
||||
|
||||
#ifdef USE_OPENSSL
|
||||
#if defined(USE_OPENSSL_DES) || defined(USE_WOLFSSL)
|
||||
/*
|
||||
* Turns a 56 bit key into the 64 bit, odd parity key and sets the key. The
|
||||
* key schedule ks is also set.
|
||||
|
@ -167,10 +164,10 @@ static void setup_des_key(const unsigned char *key_56,
|
|||
DES_set_odd_parity(&key);
|
||||
|
||||
/* Set the key */
|
||||
DES_set_key(&key, ks);
|
||||
DES_set_key_unchecked(&key, ks);
|
||||
}
|
||||
|
||||
#elif defined(USE_GNUTLS_NETTLE)
|
||||
#elif defined(USE_GNUTLS)
|
||||
|
||||
static void setup_des_key(const unsigned char *key_56,
|
||||
struct des_ctx *des)
|
||||
|
@ -187,38 +184,17 @@ static void setup_des_key(const unsigned char *key_56,
|
|||
des_set_key(des, (const uint8_t *) key);
|
||||
}
|
||||
|
||||
#elif defined(USE_GNUTLS)
|
||||
|
||||
/*
|
||||
* Turns a 56 bit key into the 64 bit, odd parity key and sets the key.
|
||||
*/
|
||||
static void setup_des_key(const unsigned char *key_56,
|
||||
gcry_cipher_hd_t *des)
|
||||
{
|
||||
char key[8];
|
||||
|
||||
/* Expand the 56-bit key to 64-bits */
|
||||
extend_key_56_to_64(key_56, key);
|
||||
|
||||
/* Set the key parity to odd */
|
||||
Curl_des_set_odd_parity((unsigned char *) key, sizeof(key));
|
||||
|
||||
/* Set the key */
|
||||
gcry_cipher_setkey(*des, key, sizeof(key));
|
||||
}
|
||||
|
||||
#elif defined(USE_NSS)
|
||||
|
||||
/*
|
||||
* Expands a 56 bit key KEY_56 to 64 bit and encrypts 64 bit of data, using
|
||||
* the expanded key. The caller is responsible for giving 64 bit of valid
|
||||
* data is IN and (at least) 64 bit large buffer as OUT.
|
||||
* encrypt_des() expands a 56 bit key KEY_56 to 64 bit and encrypts 64 bit of
|
||||
* data, using the expanded key. IN should point to 64 bits of source data,
|
||||
* OUT to a 64 bit output buffer.
|
||||
*/
|
||||
static bool encrypt_des(const unsigned char *in, unsigned char *out,
|
||||
const unsigned char *key_56)
|
||||
{
|
||||
const CK_MECHANISM_TYPE mech = CKM_DES_ECB; /* DES cipher in ECB mode */
|
||||
PK11SlotInfo *slot = NULL;
|
||||
char key[8]; /* expanded 64 bit key */
|
||||
SECItem key_item;
|
||||
PK11SymKey *symkey = NULL;
|
||||
|
@ -228,7 +204,7 @@ static bool encrypt_des(const unsigned char *in, unsigned char *out,
|
|||
bool rv = FALSE;
|
||||
|
||||
/* use internal slot for DES encryption (requires NSS to be initialized) */
|
||||
slot = PK11_GetInternalKeySlot();
|
||||
PK11SlotInfo *slot = PK11_GetInternalKeySlot();
|
||||
if(!slot)
|
||||
return FALSE;
|
||||
|
||||
|
@ -355,7 +331,7 @@ static bool encrypt_des(const unsigned char *in, unsigned char *out,
|
|||
|
||||
/* Acquire the crypto provider */
|
||||
if(!CryptAcquireContext(&hprov, NULL, NULL, PROV_RSA_FULL,
|
||||
CRYPT_VERIFYCONTEXT))
|
||||
CRYPT_VERIFYCONTEXT | CRYPT_SILENT))
|
||||
return FALSE;
|
||||
|
||||
/* Setup the key blob structure */
|
||||
|
@ -400,7 +376,7 @@ void Curl_ntlm_core_lm_resp(const unsigned char *keys,
|
|||
const unsigned char *plaintext,
|
||||
unsigned char *results)
|
||||
{
|
||||
#ifdef USE_OPENSSL
|
||||
#if defined(USE_OPENSSL_DES) || defined(USE_WOLFSSL)
|
||||
DES_key_schedule ks;
|
||||
|
||||
setup_des_key(keys, DESKEY(ks));
|
||||
|
@ -414,7 +390,7 @@ void Curl_ntlm_core_lm_resp(const unsigned char *keys,
|
|||
setup_des_key(keys + 14, DESKEY(ks));
|
||||
DES_ecb_encrypt((DES_cblock*) plaintext, (DES_cblock*) (results + 16),
|
||||
DESKEY(ks), DES_ENCRYPT);
|
||||
#elif defined(USE_GNUTLS_NETTLE)
|
||||
#elif defined(USE_GNUTLS)
|
||||
struct des_ctx des;
|
||||
setup_des_key(keys, &des);
|
||||
des_encrypt(&des, 8, results, plaintext);
|
||||
|
@ -422,23 +398,6 @@ void Curl_ntlm_core_lm_resp(const unsigned char *keys,
|
|||
des_encrypt(&des, 8, results + 8, plaintext);
|
||||
setup_des_key(keys + 14, &des);
|
||||
des_encrypt(&des, 8, results + 16, plaintext);
|
||||
#elif defined(USE_GNUTLS)
|
||||
gcry_cipher_hd_t des;
|
||||
|
||||
gcry_cipher_open(&des, GCRY_CIPHER_DES, GCRY_CIPHER_MODE_ECB, 0);
|
||||
setup_des_key(keys, &des);
|
||||
gcry_cipher_encrypt(des, results, 8, plaintext, 8);
|
||||
gcry_cipher_close(des);
|
||||
|
||||
gcry_cipher_open(&des, GCRY_CIPHER_DES, GCRY_CIPHER_MODE_ECB, 0);
|
||||
setup_des_key(keys + 7, &des);
|
||||
gcry_cipher_encrypt(des, results + 8, 8, plaintext, 8);
|
||||
gcry_cipher_close(des);
|
||||
|
||||
gcry_cipher_open(&des, GCRY_CIPHER_DES, GCRY_CIPHER_MODE_ECB, 0);
|
||||
setup_des_key(keys + 14, &des);
|
||||
gcry_cipher_encrypt(des, results + 16, 8, plaintext, 8);
|
||||
gcry_cipher_close(des);
|
||||
#elif defined(USE_NSS) || defined(USE_MBEDTLS) || defined(USE_SECTRANSP) \
|
||||
|| defined(USE_OS400CRYPTO) || defined(USE_WIN32_CRYPTO)
|
||||
encrypt_des(plaintext, results, keys);
|
||||
|
@ -450,11 +409,9 @@ void Curl_ntlm_core_lm_resp(const unsigned char *keys,
|
|||
/*
|
||||
* Set up lanmanager hashed password
|
||||
*/
|
||||
CURLcode Curl_ntlm_core_mk_lm_hash(struct Curl_easy *data,
|
||||
const char *password,
|
||||
CURLcode Curl_ntlm_core_mk_lm_hash(const char *password,
|
||||
unsigned char *lmbuffer /* 21 bytes */)
|
||||
{
|
||||
CURLcode result;
|
||||
unsigned char pw[14];
|
||||
static const unsigned char magic[] = {
|
||||
0x4B, 0x47, 0x53, 0x21, 0x40, 0x23, 0x24, 0x25 /* i.e. KGS!@#$% */
|
||||
|
@ -464,18 +421,10 @@ CURLcode Curl_ntlm_core_mk_lm_hash(struct Curl_easy *data,
|
|||
Curl_strntoupper((char *)pw, password, len);
|
||||
memset(&pw[len], 0, 14 - len);
|
||||
|
||||
/*
|
||||
* The LanManager hashed password needs to be created using the
|
||||
* password in the network encoding not the host encoding.
|
||||
*/
|
||||
result = Curl_convert_to_network(data, (char *)pw, 14);
|
||||
if(result)
|
||||
return result;
|
||||
|
||||
{
|
||||
/* Create LanManager hashed password. */
|
||||
|
||||
#ifdef USE_OPENSSL
|
||||
#if defined(USE_OPENSSL_DES) || defined(USE_WOLFSSL)
|
||||
DES_key_schedule ks;
|
||||
|
||||
setup_des_key(pw, DESKEY(ks));
|
||||
|
@ -485,24 +434,12 @@ CURLcode Curl_ntlm_core_mk_lm_hash(struct Curl_easy *data,
|
|||
setup_des_key(pw + 7, DESKEY(ks));
|
||||
DES_ecb_encrypt((DES_cblock *)magic, (DES_cblock *)(lmbuffer + 8),
|
||||
DESKEY(ks), DES_ENCRYPT);
|
||||
#elif defined(USE_GNUTLS_NETTLE)
|
||||
#elif defined(USE_GNUTLS)
|
||||
struct des_ctx des;
|
||||
setup_des_key(pw, &des);
|
||||
des_encrypt(&des, 8, lmbuffer, magic);
|
||||
setup_des_key(pw + 7, &des);
|
||||
des_encrypt(&des, 8, lmbuffer + 8, magic);
|
||||
#elif defined(USE_GNUTLS)
|
||||
gcry_cipher_hd_t des;
|
||||
|
||||
gcry_cipher_open(&des, GCRY_CIPHER_DES, GCRY_CIPHER_MODE_ECB, 0);
|
||||
setup_des_key(pw, &des);
|
||||
gcry_cipher_encrypt(des, lmbuffer, 8, magic, 8);
|
||||
gcry_cipher_close(des);
|
||||
|
||||
gcry_cipher_open(&des, GCRY_CIPHER_DES, GCRY_CIPHER_MODE_ECB, 0);
|
||||
setup_des_key(pw + 7, &des);
|
||||
gcry_cipher_encrypt(des, lmbuffer + 8, 8, magic, 8);
|
||||
gcry_cipher_close(des);
|
||||
#elif defined(USE_NSS) || defined(USE_MBEDTLS) || defined(USE_SECTRANSP) \
|
||||
|| defined(USE_OS400CRYPTO) || defined(USE_WIN32_CRYPTO)
|
||||
encrypt_des(magic, lmbuffer, pw);
|
||||
|
@ -515,7 +452,6 @@ CURLcode Curl_ntlm_core_mk_lm_hash(struct Curl_easy *data,
|
|||
return CURLE_OK;
|
||||
}
|
||||
|
||||
#ifdef USE_NTRESPONSES
|
||||
static void ascii_to_unicode_le(unsigned char *dest, const char *src,
|
||||
size_t srclen)
|
||||
{
|
||||
|
@ -526,7 +462,7 @@ static void ascii_to_unicode_le(unsigned char *dest, const char *src,
|
|||
}
|
||||
}
|
||||
|
||||
#if defined(USE_NTLM_V2) && !defined(USE_WINDOWS_SSPI)
|
||||
#if !defined(USE_WINDOWS_SSPI)
|
||||
|
||||
static void ascii_uppercase_to_unicode_le(unsigned char *dest,
|
||||
const char *src, size_t srclen)
|
||||
|
@ -538,111 +474,84 @@ static void ascii_uppercase_to_unicode_le(unsigned char *dest,
|
|||
}
|
||||
}
|
||||
|
||||
#endif /* USE_NTLM_V2 && !USE_WINDOWS_SSPI */
|
||||
#endif /* !USE_WINDOWS_SSPI */
|
||||
|
||||
/*
|
||||
* Set up nt hashed passwords
|
||||
* @unittest: 1600
|
||||
*/
|
||||
CURLcode Curl_ntlm_core_mk_nt_hash(struct Curl_easy *data,
|
||||
const char *password,
|
||||
CURLcode Curl_ntlm_core_mk_nt_hash(const char *password,
|
||||
unsigned char *ntbuffer /* 21 bytes */)
|
||||
{
|
||||
size_t len = strlen(password);
|
||||
unsigned char *pw;
|
||||
CURLcode result;
|
||||
if(len > SIZE_T_MAX/2) /* avoid integer overflow */
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
pw = len ? malloc(len * 2) : strdup("");
|
||||
pw = len ? malloc(len * 2) : (unsigned char *)strdup("");
|
||||
if(!pw)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
||||
ascii_to_unicode_le(pw, password, len);
|
||||
|
||||
/*
|
||||
* The NT hashed password needs to be created using the password in the
|
||||
* network encoding not the host encoding.
|
||||
*/
|
||||
result = Curl_convert_to_network(data, (char *)pw, len * 2);
|
||||
if(result)
|
||||
return result;
|
||||
|
||||
{
|
||||
/* Create NT hashed password. */
|
||||
#ifdef USE_OPENSSL
|
||||
#if !defined(OPENSSL_NO_MD4)
|
||||
MD4_CTX MD4pw;
|
||||
MD4_Init(&MD4pw);
|
||||
MD4_Update(&MD4pw, pw, 2 * len);
|
||||
MD4_Final(ntbuffer, &MD4pw);
|
||||
#else
|
||||
Curl_md4it(ntbuffer, pw, 2 * len);
|
||||
#endif
|
||||
#elif defined(USE_GNUTLS_NETTLE)
|
||||
struct md4_ctx MD4pw;
|
||||
md4_init(&MD4pw);
|
||||
md4_update(&MD4pw, (unsigned int)(2 * len), pw);
|
||||
md4_digest(&MD4pw, MD4_DIGEST_SIZE, ntbuffer);
|
||||
#elif defined(USE_GNUTLS)
|
||||
gcry_md_hd_t MD4pw;
|
||||
gcry_md_open(&MD4pw, GCRY_MD_MD4, 0);
|
||||
gcry_md_write(MD4pw, pw, 2 * len);
|
||||
memcpy(ntbuffer, gcry_md_read(MD4pw, 0), MD4_DIGEST_LENGTH);
|
||||
gcry_md_close(MD4pw);
|
||||
#elif defined(USE_NSS)
|
||||
Curl_md4it(ntbuffer, pw, 2 * len);
|
||||
#elif defined(USE_MBEDTLS)
|
||||
#if defined(MBEDTLS_MD4_C)
|
||||
mbedtls_md4(pw, 2 * len, ntbuffer);
|
||||
#else
|
||||
Curl_md4it(ntbuffer, pw, 2 * len);
|
||||
#endif
|
||||
#elif defined(USE_SECTRANSP)
|
||||
(void)CC_MD4(pw, (CC_LONG)(2 * len), ntbuffer);
|
||||
#elif defined(USE_OS400CRYPTO)
|
||||
Curl_md4it(ntbuffer, pw, 2 * len);
|
||||
#elif defined(USE_WIN32_CRYPTO)
|
||||
HCRYPTPROV hprov;
|
||||
if(CryptAcquireContext(&hprov, NULL, NULL, PROV_RSA_FULL,
|
||||
CRYPT_VERIFYCONTEXT)) {
|
||||
HCRYPTHASH hhash;
|
||||
if(CryptCreateHash(hprov, CALG_MD4, 0, 0, &hhash)) {
|
||||
DWORD length = 16;
|
||||
CryptHashData(hhash, pw, (unsigned int)len * 2, 0);
|
||||
CryptGetHashParam(hhash, HP_HASHVAL, ntbuffer, &length, 0);
|
||||
CryptDestroyHash(hhash);
|
||||
}
|
||||
CryptReleaseContext(hprov, 0);
|
||||
}
|
||||
#endif
|
||||
|
||||
memset(ntbuffer + 16, 0, 21 - 16);
|
||||
}
|
||||
/* Create NT hashed password. */
|
||||
Curl_md4it(ntbuffer, pw, 2 * len);
|
||||
memset(ntbuffer + 16, 0, 21 - 16);
|
||||
|
||||
free(pw);
|
||||
|
||||
return CURLE_OK;
|
||||
}
|
||||
|
||||
#if defined(USE_NTLM_V2) && !defined(USE_WINDOWS_SSPI)
|
||||
#if !defined(USE_WINDOWS_SSPI)
|
||||
|
||||
/* This returns the HMAC MD5 digest */
|
||||
static CURLcode hmac_md5(const unsigned char *key, unsigned int keylen,
|
||||
const unsigned char *data, unsigned int datalen,
|
||||
unsigned char *output)
|
||||
/* Timestamp in tenths of a microsecond since January 1, 1601 00:00:00 UTC. */
|
||||
struct ms_filetime {
|
||||
unsigned int dwLowDateTime;
|
||||
unsigned int dwHighDateTime;
|
||||
};
|
||||
|
||||
/* Convert a time_t to an MS FILETIME (MS-DTYP section 2.3.3). */
|
||||
static void time2filetime(struct ms_filetime *ft, time_t t)
|
||||
{
|
||||
HMAC_context *ctxt = Curl_HMAC_init(Curl_HMAC_MD5, key, keylen);
|
||||
#if SIZEOF_TIME_T > 4
|
||||
t = (t + CURL_OFF_T_C(11644473600)) * 10000000;
|
||||
ft->dwLowDateTime = (unsigned int) (t & 0xFFFFFFFF);
|
||||
ft->dwHighDateTime = (unsigned int) (t >> 32);
|
||||
#else
|
||||
unsigned int r, s;
|
||||
unsigned int i;
|
||||
|
||||
if(!ctxt)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
ft->dwLowDateTime = t & 0xFFFFFFFF;
|
||||
ft->dwHighDateTime = 0;
|
||||
|
||||
/* Update the digest with the given challenge */
|
||||
Curl_HMAC_update(ctxt, data, datalen);
|
||||
# ifndef HAVE_TIME_T_UNSIGNED
|
||||
/* Extend sign if needed. */
|
||||
if(ft->dwLowDateTime & 0x80000000)
|
||||
ft->dwHighDateTime = ~0;
|
||||
# endif
|
||||
|
||||
/* Finalise the digest */
|
||||
Curl_HMAC_final(ctxt, output);
|
||||
/* Bias seconds to Jan 1, 1601.
|
||||
134774 days = 11644473600 seconds = 0x2B6109100 */
|
||||
r = ft->dwLowDateTime;
|
||||
ft->dwLowDateTime = (ft->dwLowDateTime + 0xB6109100U) & 0xFFFFFFFF;
|
||||
ft->dwHighDateTime += ft->dwLowDateTime < r? 0x03: 0x02;
|
||||
|
||||
return CURLE_OK;
|
||||
/* Convert to tenths of microseconds. */
|
||||
ft->dwHighDateTime *= 10000000;
|
||||
i = 32;
|
||||
do {
|
||||
i -= 8;
|
||||
s = ((ft->dwLowDateTime >> i) & 0xFF) * (10000000 - 1);
|
||||
r = (s << i) & 0xFFFFFFFF;
|
||||
s >>= 1; /* Split shift to avoid width overflow. */
|
||||
s >>= 31 - i;
|
||||
ft->dwLowDateTime = (ft->dwLowDateTime + r) & 0xFFFFFFFF;
|
||||
if(ft->dwLowDateTime < r)
|
||||
s++;
|
||||
ft->dwHighDateTime += s;
|
||||
} while(i);
|
||||
ft->dwHighDateTime &= 0xFFFFFFFF;
|
||||
#endif
|
||||
}
|
||||
|
||||
/* This creates the NTLMv2 hash by using NTLM hash as the key and Unicode
|
||||
|
@ -658,15 +567,11 @@ CURLcode Curl_ntlm_core_mk_ntlmv2_hash(const char *user, size_t userlen,
|
|||
unsigned char *identity;
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
/* we do the length checks below separately to avoid integer overflow risk
|
||||
on extreme data lengths */
|
||||
if((userlen > SIZE_T_MAX/2) ||
|
||||
(domlen > SIZE_T_MAX/2) ||
|
||||
((userlen + domlen) > SIZE_T_MAX/2))
|
||||
if((userlen > CURL_MAX_INPUT_LENGTH) || (domlen > CURL_MAX_INPUT_LENGTH))
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
||||
identity_len = (userlen + domlen) * 2;
|
||||
identity = malloc(identity_len);
|
||||
identity = malloc(identity_len + 1);
|
||||
|
||||
if(!identity)
|
||||
return CURLE_OUT_OF_MEMORY;
|
||||
|
@ -674,8 +579,8 @@ CURLcode Curl_ntlm_core_mk_ntlmv2_hash(const char *user, size_t userlen,
|
|||
ascii_uppercase_to_unicode_le(identity, user, userlen);
|
||||
ascii_to_unicode_le(identity + (userlen << 1), domain, domlen);
|
||||
|
||||
result = hmac_md5(ntlmhash, 16, identity, curlx_uztoui(identity_len),
|
||||
ntlmv2hash);
|
||||
result = Curl_hmacit(Curl_HMAC_MD5, ntlmhash, 16, identity, identity_len,
|
||||
ntlmv2hash);
|
||||
free(identity);
|
||||
|
||||
return result;
|
||||
|
@ -721,26 +626,22 @@ CURLcode Curl_ntlm_core_mk_ntlmv2_resp(unsigned char *ntlmv2hash,
|
|||
|
||||
unsigned int len = 0;
|
||||
unsigned char *ptr = NULL;
|
||||
unsigned char hmac_output[NTLM_HMAC_MD5_LEN];
|
||||
curl_off_t tw;
|
||||
unsigned char hmac_output[HMAC_MD5_LENGTH];
|
||||
struct ms_filetime tw;
|
||||
|
||||
CURLcode result = CURLE_OK;
|
||||
|
||||
#if CURL_SIZEOF_CURL_OFF_T < 8
|
||||
#error "this section needs 64bit support to work"
|
||||
#endif
|
||||
|
||||
/* Calculate the timestamp */
|
||||
#ifdef DEBUGBUILD
|
||||
char *force_timestamp = getenv("CURL_FORCETIME");
|
||||
if(force_timestamp)
|
||||
tw = CURL_OFF_T_C(11644473600) * 10000000;
|
||||
time2filetime(&tw, (time_t) 0);
|
||||
else
|
||||
#endif
|
||||
tw = ((curl_off_t)time(NULL) + CURL_OFF_T_C(11644473600)) * 10000000;
|
||||
time2filetime(&tw, time(NULL));
|
||||
|
||||
/* Calculate the response len */
|
||||
len = NTLM_HMAC_MD5_LEN + NTLMv2_BLOB_LEN;
|
||||
len = HMAC_MD5_LENGTH + NTLMv2_BLOB_LEN;
|
||||
|
||||
/* Allocate the response */
|
||||
ptr = calloc(1, len);
|
||||
|
@ -748,20 +649,22 @@ CURLcode Curl_ntlm_core_mk_ntlmv2_resp(unsigned char *ntlmv2hash,
|
|||
return CURLE_OUT_OF_MEMORY;
|
||||
|
||||
/* Create the BLOB structure */
|
||||
msnprintf((char *)ptr + NTLM_HMAC_MD5_LEN, NTLMv2_BLOB_LEN,
|
||||
"%c%c%c%c" /* NTLMv2_BLOB_SIGNATURE */
|
||||
"%c%c%c%c", /* Reserved = 0 */
|
||||
msnprintf((char *)ptr + HMAC_MD5_LENGTH, NTLMv2_BLOB_LEN,
|
||||
"%c%c%c%c" /* NTLMv2_BLOB_SIGNATURE */
|
||||
"%c%c%c%c" /* Reserved = 0 */
|
||||
"%c%c%c%c%c%c%c%c", /* Timestamp */
|
||||
NTLMv2_BLOB_SIGNATURE[0], NTLMv2_BLOB_SIGNATURE[1],
|
||||
NTLMv2_BLOB_SIGNATURE[2], NTLMv2_BLOB_SIGNATURE[3],
|
||||
0, 0, 0, 0);
|
||||
0, 0, 0, 0,
|
||||
LONGQUARTET(tw.dwLowDateTime), LONGQUARTET(tw.dwHighDateTime));
|
||||
|
||||
Curl_write64_le(tw, ptr + 24);
|
||||
memcpy(ptr + 32, challenge_client, 8);
|
||||
memcpy(ptr + 44, ntlm->target_info, ntlm->target_info_len);
|
||||
if(ntlm->target_info_len)
|
||||
memcpy(ptr + 44, ntlm->target_info, ntlm->target_info_len);
|
||||
|
||||
/* Concatenate the Type 2 challenge with the BLOB and do HMAC MD5 */
|
||||
memcpy(ptr + 8, &ntlm->nonce[0], 8);
|
||||
result = hmac_md5(ntlmv2hash, NTLM_HMAC_MD5_LEN, ptr + 8,
|
||||
result = Curl_hmacit(Curl_HMAC_MD5, ntlmv2hash, HMAC_MD5_LENGTH, ptr + 8,
|
||||
NTLMv2_BLOB_LEN + 8, hmac_output);
|
||||
if(result) {
|
||||
free(ptr);
|
||||
|
@ -769,7 +672,7 @@ CURLcode Curl_ntlm_core_mk_ntlmv2_resp(unsigned char *ntlmv2hash,
|
|||
}
|
||||
|
||||
/* Concatenate the HMAC MD5 output with the BLOB */
|
||||
memcpy(ptr, hmac_output, NTLM_HMAC_MD5_LEN);
|
||||
memcpy(ptr, hmac_output, HMAC_MD5_LENGTH);
|
||||
|
||||
/* Return the response */
|
||||
*ntresp = ptr;
|
||||
|
@ -804,7 +707,8 @@ CURLcode Curl_ntlm_core_mk_lmv2_resp(unsigned char *ntlmv2hash,
|
|||
memcpy(&data[0], challenge_server, 8);
|
||||
memcpy(&data[8], challenge_client, 8);
|
||||
|
||||
result = hmac_md5(ntlmv2hash, 16, &data[0], 16, hmac_output);
|
||||
result = Curl_hmacit(Curl_HMAC_MD5, ntlmv2hash, 16, &data[0], 16,
|
||||
hmac_output);
|
||||
if(result)
|
||||
return result;
|
||||
|
||||
|
@ -815,10 +719,6 @@ CURLcode Curl_ntlm_core_mk_lmv2_resp(unsigned char *ntlmv2hash,
|
|||
return result;
|
||||
}
|
||||
|
||||
#endif /* USE_NTLM_V2 && !USE_WINDOWS_SSPI */
|
||||
#endif /* !USE_WINDOWS_SSPI */
|
||||
|
||||
#endif /* USE_NTRESPONSES */
|
||||
|
||||
#endif /* !USE_WINDOWS_SSPI || USE_WIN32_CRYPTO */
|
||||
|
||||
#endif /* USE_NTLM */
|
||||
#endif /* USE_CURL_NTLM_CORE */
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
* | (__| |_| | _ <| |___
|
||||
* \___|\___/|_| \_\_____|
|
||||
*
|
||||
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
* Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||
*
|
||||
* This software is licensed as described in the file COPYING, which
|
||||
* you should have received as part of this distribution. The terms
|
||||
* are also available at https://curl.haxx.se/docs/copyright.html.
|
||||
* are also available at https://curl.se/docs/copyright.html.
|
||||
*
|
||||
* You may opt to use, copy, modify, merge, publish, distribute and/or sell
|
||||
* copies of the Software, and permit persons to whom the Software is
|
||||
|
@ -20,59 +20,46 @@
|
|||
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
||||
* KIND, either express or implied.
|
||||
*
|
||||
* SPDX-License-Identifier: curl
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include "curl_setup.h"
|
||||
|
||||
#if defined(USE_NTLM)
|
||||
#if defined(USE_CURL_NTLM_CORE)
|
||||
|
||||
/* If NSS is the first available SSL backend (see order in curl_ntlm_core.c)
|
||||
then it must be initialized to be used by NTLM. */
|
||||
#if !defined(USE_OPENSSL) && \
|
||||
!defined(USE_GNUTLS_NETTLE) && \
|
||||
!defined(USE_WOLFSSL) && \
|
||||
!defined(USE_GNUTLS) && \
|
||||
defined(USE_NSS)
|
||||
#define NTLM_NEEDS_NSS_INIT
|
||||
#endif
|
||||
|
||||
#if !defined(USE_WINDOWS_SSPI) || defined(USE_WIN32_CRYPTO)
|
||||
|
||||
#ifdef USE_OPENSSL
|
||||
#if defined(USE_OPENSSL)
|
||||
# include <openssl/ssl.h>
|
||||
#elif defined(USE_WOLFSSL)
|
||||
# include <wolfssl/options.h>
|
||||
# include <wolfssl/openssl/ssl.h>
|
||||
#endif
|
||||
|
||||
/* Define USE_NTRESPONSES in order to make the type-3 message include
|
||||
* the NT response message. */
|
||||
#define USE_NTRESPONSES
|
||||
|
||||
/* Define USE_NTLM2SESSION in order to make the type-3 message include the
|
||||
NTLM2Session response message, requires USE_NTRESPONSES defined to 1 and a
|
||||
Crypto engine that we have curl_ssl_md5sum() for. */
|
||||
#if defined(USE_NTRESPONSES) && !defined(USE_WIN32_CRYPTO)
|
||||
#define USE_NTLM2SESSION
|
||||
#endif
|
||||
|
||||
/* Define USE_NTLM_V2 in order to allow the type-3 message to include the
|
||||
LMv2 and NTLMv2 response messages, requires USE_NTRESPONSES defined to 1
|
||||
and support for 64-bit integers. */
|
||||
#if defined(USE_NTRESPONSES) && (CURL_SIZEOF_CURL_OFF_T > 4)
|
||||
#define USE_NTLM_V2
|
||||
#endif
|
||||
/* Helpers to generate function byte arguments in little endian order */
|
||||
#define SHORTPAIR(x) ((int)((x) & 0xff)), ((int)(((x) >> 8) & 0xff))
|
||||
#define LONGQUARTET(x) ((int)((x) & 0xff)), ((int)(((x) >> 8) & 0xff)), \
|
||||
((int)(((x) >> 16) & 0xff)), ((int)(((x) >> 24) & 0xff))
|
||||
|
||||
void Curl_ntlm_core_lm_resp(const unsigned char *keys,
|
||||
const unsigned char *plaintext,
|
||||
unsigned char *results);
|
||||
|
||||
CURLcode Curl_ntlm_core_mk_lm_hash(struct Curl_easy *data,
|
||||
const char *password,
|
||||
CURLcode Curl_ntlm_core_mk_lm_hash(const char *password,
|
||||
unsigned char *lmbuffer /* 21 bytes */);
|
||||
|
||||
#ifdef USE_NTRESPONSES
|
||||
CURLcode Curl_ntlm_core_mk_nt_hash(struct Curl_easy *data,
|
||||
const char *password,
|
||||
CURLcode Curl_ntlm_core_mk_nt_hash(const char *password,
|
||||
unsigned char *ntbuffer /* 21 bytes */);
|
||||
|
||||
#if defined(USE_NTLM_V2) && !defined(USE_WINDOWS_SSPI)
|
||||
#if !defined(USE_WINDOWS_SSPI)
|
||||
|
||||
CURLcode Curl_hmac_md5(const unsigned char *key, unsigned int keylen,
|
||||
const unsigned char *data, unsigned int datalen,
|
||||
|
@ -94,12 +81,8 @@ CURLcode Curl_ntlm_core_mk_lmv2_resp(unsigned char *ntlmv2hash,
|
|||
unsigned char *challenge_server,
|
||||
unsigned char *lmresp);
|
||||
|
||||
#endif /* USE_NTLM_V2 && !USE_WINDOWS_SSPI */
|
||||
#endif /* !USE_WINDOWS_SSPI */
|
||||
|
||||
#endif /* USE_NTRESPONSES */
|
||||
|
||||
#endif /* !USE_WINDOWS_SSPI || USE_WIN32_CRYPTO */
|
||||
|
||||
#endif /* USE_NTLM */
|
||||
#endif /* USE_CURL_NTLM_CORE */
|
||||
|
||||
#endif /* HEADER_CURL_NTLM_CORE_H */
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue