[CVE-2017-9502] url: fix buffer overwrite with file protocol
[platform/upstream/curl.git] / CMakeLists.txt
1 #***************************************************************************
2 #                                  _   _ ____  _
3 #  Project                     ___| | | |  _ \| |
4 #                             / __| | | | |_) | |
5 #                            | (__| |_| |  _ <| |___
6 #                             \___|\___/|_| \_\_____|
7 #
8 # Copyright (C) 1998 - 2016, Daniel Stenberg, <daniel@haxx.se>, et al.
9 #
10 # This software is licensed as described in the file COPYING, which
11 # you should have received as part of this distribution. The terms
12 # are also available at https://curl.haxx.se/docs/copyright.html.
13 #
14 # You may opt to use, copy, modify, merge, publish, distribute and/or sell
15 # copies of the Software, and permit persons to whom the Software is
16 # furnished to do so, under the terms of the COPYING file.
17 #
18 # This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
19 # KIND, either express or implied.
20 #
21 ###########################################################################
22 # curl/libcurl CMake script
23 # by Tetetest and Sukender (Benoit Neil)
24
25 # TODO:
26 # The output .so file lacks the soname number which we currently have within the lib/Makefile.am file
27 # Add full (4 or 5 libs) SSL support
28 # Add INSTALL target (EXTRA_DIST variables in Makefile.am may be moved to Makefile.inc so that CMake/CPack is aware of what's to include).
29 # Add CTests(?)
30 # Check on all possible platforms
31 # Test with as many configurations possible (With or without any option)
32 # Create scripts that help keeping the CMake build system up to date (to reduce maintenance). According to Tetetest:
33 #  - lists of headers that 'configure' checks for;
34 #  - curl-specific tests (the ones that are in m4/curl-*.m4 files);
35 #  - (most obvious thing:) curl version numbers.
36 # Add documentation subproject
37 #
38 # To check:
39 # (From Daniel Stenberg) The cmake build selected to run gcc with -fPIC on my box while the plain configure script did not.
40 # (From Daniel Stenberg) The gcc command line use neither -g nor any -O options. As a developer, I also treasure our configure scripts's --enable-debug option that sets a long range of "picky" compiler options.
41 cmake_minimum_required(VERSION 2.8 FATAL_ERROR)
42 set(CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/CMake;${CMAKE_MODULE_PATH}")
43 include(Utilities)
44 include(Macros)
45 include(CMakeDependentOption)
46
47 project( CURL C )
48
49 message(WARNING "the curl cmake build system is poorly maintained. Be aware")
50
51 file (READ ${CURL_SOURCE_DIR}/include/curl/curlver.h CURL_VERSION_H_CONTENTS)
52 string (REGEX MATCH "#define LIBCURL_VERSION \"[^\"]*"
53   CURL_VERSION ${CURL_VERSION_H_CONTENTS})
54 string (REGEX REPLACE "[^\"]+\"" "" CURL_VERSION ${CURL_VERSION})
55 string (REGEX MATCH "#define LIBCURL_VERSION_NUM 0x[0-9a-fA-F]+"
56   CURL_VERSION_NUM ${CURL_VERSION_H_CONTENTS})
57 string (REGEX REPLACE "[^0]+0x" "" CURL_VERSION_NUM ${CURL_VERSION_NUM})
58
59 include_regular_expression("^.*$")    # Sukender: Is it necessary?
60
61 # Setup package meta-data
62 # SET(PACKAGE "curl")
63 message(STATUS "curl version=[${CURL_VERSION}]")
64 # SET(PACKAGE_TARNAME "curl")
65 # SET(PACKAGE_NAME "curl")
66 # SET(PACKAGE_VERSION "-")
67 # SET(PACKAGE_STRING "curl-")
68 # SET(PACKAGE_BUGREPORT "a suitable curl mailing list => https://curl.haxx.se/mail/")
69 set(OPERATING_SYSTEM "${CMAKE_SYSTEM_NAME}")
70 set(OS "\"${CMAKE_SYSTEM_NAME}\"")
71
72 include_directories(${PROJECT_BINARY_DIR}/include/curl)
73 include_directories( ${CURL_SOURCE_DIR}/include )
74
75 option(BUILD_CURL_EXE "Set to ON to build curl executable." ON)
76 option(CURL_STATICLIB "Set to ON to build libcurl with static linking." OFF)
77 option(ENABLE_ARES "Set to ON to enable c-ares support" OFF)
78 if(WIN32)
79   CMAKE_DEPENDENT_OPTION(ENABLE_THREADED_RESOLVER
80                          "Set to ON to enable threaded DNS lookup"
81                          ON "NOT ENABLE_ARES"
82                          OFF)
83 else()
84   option(ENABLE_THREADED_RESOLVER "Set to ON to enable POSIX threaded DNS lookup" OFF)
85 endif()
86 option(ENABLE_DEBUG "Set to ON to enable curl debug features" OFF)
87 option(ENABLE_CURLDEBUG "Set to ON to build with TrackMemory feature enabled" OFF)
88
89 if (ENABLE_DEBUG)
90   # DEBUGBUILD will be defined only for Debug builds
91   if(NOT CMAKE_VERSION VERSION_LESS 3.0)
92     set_property(DIRECTORY APPEND PROPERTY COMPILE_DEFINITIONS $<$<CONFIG:Debug>:DEBUGBUILD>)
93   else()
94     set_property(DIRECTORY APPEND PROPERTY COMPILE_DEFINITIONS_DEBUG DEBUGBUILD)
95   endif()
96   set(ENABLE_CURLDEBUG ON)
97 endif()
98
99 if (ENABLE_CURLDEBUG)
100   set_property(DIRECTORY APPEND PROPERTY COMPILE_DEFINITIONS CURLDEBUG)
101 endif()
102
103 # initialize CURL_LIBS
104 set(CURL_LIBS "")
105
106 if(ENABLE_THREADED_RESOLVER AND ENABLE_ARES)
107   message(FATAL_ERROR "Options ENABLE_THREADED_RESOLVER and ENABLE_ARES are mutually exclusive")
108 endif()
109
110 if(ENABLE_ARES)
111   set(USE_ARES 1)
112   find_package(CARES REQUIRED)
113   list(APPEND CURL_LIBS ${CARES_LIBRARY} )
114   set(CURL_LIBS ${CURL_LIBS} ${CARES_LIBRARY})
115 endif()
116
117 if(MSVC)
118   option(BUILD_RELEASE_DEBUG_DIRS "Set OFF to build each configuration to a separate directory" OFF)
119   mark_as_advanced(BUILD_RELEASE_DEBUG_DIRS)
120 endif()
121
122 include(CurlSymbolHiding)
123
124 option(HTTP_ONLY "disables all protocols except HTTP (This overrides all CURL_DISABLE_* options)" OFF)
125 mark_as_advanced(HTTP_ONLY)
126 option(CURL_DISABLE_FTP "disables FTP" OFF)
127 mark_as_advanced(CURL_DISABLE_FTP)
128 option(CURL_DISABLE_LDAP "disables LDAP" OFF)
129 mark_as_advanced(CURL_DISABLE_LDAP)
130 option(CURL_DISABLE_TELNET "disables Telnet" OFF)
131 mark_as_advanced(CURL_DISABLE_TELNET)
132 option(CURL_DISABLE_DICT "disables DICT" OFF)
133 mark_as_advanced(CURL_DISABLE_DICT)
134 option(CURL_DISABLE_FILE "disables FILE" OFF)
135 mark_as_advanced(CURL_DISABLE_FILE)
136 option(CURL_DISABLE_TFTP "disables TFTP" OFF)
137 mark_as_advanced(CURL_DISABLE_TFTP)
138 option(CURL_DISABLE_HTTP "disables HTTP" OFF)
139 mark_as_advanced(CURL_DISABLE_HTTP)
140
141 option(CURL_DISABLE_LDAPS "to disable LDAPS" OFF)
142 mark_as_advanced(CURL_DISABLE_LDAPS)
143
144 option(CURL_DISABLE_RTSP "to disable RTSP" OFF)
145 mark_as_advanced(CURL_DISABLE_RTSP)
146 option(CURL_DISABLE_PROXY "to disable proxy" OFF)
147 mark_as_advanced(CURL_DISABLE_PROXY)
148 option(CURL_DISABLE_POP3 "to disable POP3" OFF)
149 mark_as_advanced(CURL_DISABLE_POP3)
150 option(CURL_DISABLE_IMAP "to disable IMAP" OFF)
151 mark_as_advanced(CURL_DISABLE_IMAP)
152 option(CURL_DISABLE_SMTP "to disable SMTP" OFF)
153 mark_as_advanced(CURL_DISABLE_SMTP)
154 option(CURL_DISABLE_GOPHER "to disable Gopher" OFF)
155 mark_as_advanced(CURL_DISABLE_GOPHER)
156
157 if(HTTP_ONLY)
158   set(CURL_DISABLE_FTP ON)
159   set(CURL_DISABLE_LDAP ON)
160   set(CURL_DISABLE_LDAPS ON)
161   set(CURL_DISABLE_TELNET ON)
162   set(CURL_DISABLE_DICT ON)
163   set(CURL_DISABLE_FILE ON)
164   set(CURL_DISABLE_TFTP ON)
165   set(CURL_DISABLE_RTSP ON)
166   set(CURL_DISABLE_POP3 ON)
167   set(CURL_DISABLE_IMAP ON)
168   set(CURL_DISABLE_SMTP ON)
169   set(CURL_DISABLE_GOPHER ON)
170 endif()
171
172 option(CURL_DISABLE_COOKIES "to disable cookies support" OFF)
173 mark_as_advanced(CURL_DISABLE_COOKIES)
174
175 option(CURL_DISABLE_CRYPTO_AUTH "to disable cryptographic authentication" OFF)
176 mark_as_advanced(CURL_DISABLE_CRYPTO_AUTH)
177 option(CURL_DISABLE_VERBOSE_STRINGS "to disable verbose strings" OFF)
178 mark_as_advanced(CURL_DISABLE_VERBOSE_STRINGS)
179 option(DISABLED_THREADSAFE "Set to explicitly specify we don't want to use thread-safe functions" OFF)
180 mark_as_advanced(DISABLED_THREADSAFE)
181 option(ENABLE_IPV6 "Define if you want to enable IPv6 support" ON)
182 mark_as_advanced(ENABLE_IPV6)
183 if(ENABLE_IPV6 AND NOT WIN32)
184   include(CheckStructHasMember)
185   check_struct_has_member("struct sockaddr_in6" sin6_addr "netinet/in.h"
186                           HAVE_SOCKADDR_IN6_SIN6_ADDR)
187   check_struct_has_member("struct sockaddr_in6" sin6_scope_id "netinet/in.h"
188                           HAVE_SOCKADDR_IN6_SIN6_SCOPE_ID)
189   if(NOT HAVE_SOCKADDR_IN6_SIN6_ADDR)
190     message(WARNING "struct sockaddr_in6 not available, disabling IPv6 support")
191     # Force the feature off as this name is used as guard macro...
192     set(ENABLE_IPV6 OFF
193         CACHE BOOL "Define if you want to enable IPv6 support" FORCE)
194   endif()
195 endif()
196
197 option(ENABLE_MANUAL "to provide the built-in manual" ON)
198 unset(USE_MANUAL CACHE) # TODO: cache NROFF/NROFF_MANOPT/USE_MANUAL vars?
199 if(ENABLE_MANUAL)
200   find_program(NROFF NAMES gnroff nroff)
201   if(NROFF)
202     # Need a way to write to stdin, this will do
203     file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/nroff-input.txt" "test")
204     # Tests for a valid nroff option to generate a manpage
205     foreach(_MANOPT "-man" "-mandoc")
206       execute_process(COMMAND "${NROFF}" ${_MANOPT}
207         OUTPUT_VARIABLE NROFF_MANOPT_OUTPUT
208         INPUT_FILE "${CMAKE_CURRENT_BINARY_DIR}/nroff-input.txt"
209         ERROR_QUIET)
210       # Save the option if it was valid
211       if(NROFF_MANOPT_OUTPUT)
212         message("Found *nroff option: -- ${_MANOPT}")
213         set(NROFF_MANOPT ${_MANOPT})
214         set(USE_MANUAL 1)
215         break()
216       endif()
217     endforeach()
218     # No need for the temporary file
219     file(REMOVE "${CMAKE_CURRENT_BINARY_DIR}/nroff-input.txt")
220     if(NOT USE_MANUAL)
221       message(WARNING "Found no *nroff option to get plaintext from man pages")
222     endif()
223   else()
224     message(WARNING "Found no *nroff program")
225   endif()
226 endif()
227
228 # We need ansi c-flags, especially on HP
229 set(CMAKE_C_FLAGS "${CMAKE_ANSI_CFLAGS} ${CMAKE_C_FLAGS}")
230 set(CMAKE_REQUIRED_FLAGS ${CMAKE_ANSI_CFLAGS})
231
232 # Disable warnings on Borland to avoid changing 3rd party code.
233 if(BORLAND)
234   set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -w-")
235 endif(BORLAND)
236
237 # If we are on AIX, do the _ALL_SOURCE magic
238 if(${CMAKE_SYSTEM_NAME} MATCHES AIX)
239   set(_ALL_SOURCE 1)
240 endif(${CMAKE_SYSTEM_NAME} MATCHES AIX)
241
242 # Include all the necessary files for macros
243 include (CheckFunctionExists)
244 include (CheckIncludeFile)
245 include (CheckIncludeFiles)
246 include (CheckLibraryExists)
247 include (CheckSymbolExists)
248 include (CheckTypeSize)
249 include (CheckCSourceCompiles)
250 include (CMakeDependentOption)
251
252 # On windows preload settings
253 if(WIN32)
254   set(CMAKE_REQUIRED_DEFINITIONS "${CMAKE_REQUIRED_DEFINITIONS} -D_WINSOCKAPI_=")
255   include(${CMAKE_CURRENT_SOURCE_DIR}/CMake/Platforms/WindowsCache.cmake)
256 endif(WIN32)
257
258 if(ENABLE_THREADED_RESOLVER)
259   if(WIN32)
260     set(USE_THREADS_WIN32 ON)
261   else()
262     check_include_file_concat("pthread.h" HAVE_PTHREAD_H)
263     if(HAVE_PTHREAD_H)
264       set(CMAKE_THREAD_PREFER_PTHREAD 1)
265       find_package(Threads)
266       if(CMAKE_USE_PTHREADS_INIT)
267         set(CURL_LIBS ${CURL_LIBS} ${CMAKE_THREAD_LIBS_INIT})
268         set(USE_THREADS_POSIX 1)
269       endif()
270     endif()
271   endif()
272 endif()
273
274 # Check for all needed libraries
275 check_library_exists_concat("dl"     dlopen       HAVE_LIBDL)
276 check_library_exists_concat("socket" connect      HAVE_LIBSOCKET)
277 check_library_exists("c" gethostbyname "" NOT_NEED_LIBNSL)
278
279 # Yellowtab Zeta needs different libraries than BeOS 5.
280 if(BEOS)
281   set(NOT_NEED_LIBNSL 1)
282   check_library_exists_concat("bind" gethostbyname HAVE_LIBBIND)
283   check_library_exists_concat("bnetapi" closesocket HAVE_LIBBNETAPI)
284 endif(BEOS)
285
286 if(NOT NOT_NEED_LIBNSL)
287   check_library_exists_concat("nsl"    gethostbyname  HAVE_LIBNSL)
288 endif(NOT NOT_NEED_LIBNSL)
289
290 check_function_exists(gethostname HAVE_GETHOSTNAME)
291
292 set(OPENSSL_DEFAULT ON)
293 if(WIN32)
294   set(OPENSSL_DEFAULT OFF)
295   check_library_exists_concat("ws2_32" getch        HAVE_LIBWS2_32)
296   check_library_exists_concat("winmm"  getch        HAVE_LIBWINMM)
297 endif()
298
299 option(CMAKE_USE_OPENSSL "Use OpenSSL code. Experimental" ${OPENSSL_DEFAULT})
300 mark_as_advanced(CMAKE_USE_OPENSSL)
301
302 if(WIN32)
303   CMAKE_DEPENDENT_OPTION(CURL_WINDOWS_SSPI "Use windows libraries to allow NTLM authentication without openssl" ON
304     "NOT CMAKE_USE_OPENSSL" OFF)
305   mark_as_advanced(CURL_WINDOWS_SSPI)
306 endif()
307
308 set(USE_OPENSSL OFF)
309 set(HAVE_LIBCRYPTO OFF)
310 set(HAVE_LIBSSL OFF)
311
312 if(CMAKE_USE_OPENSSL)
313   find_package(OpenSSL)
314   if(OPENSSL_FOUND)
315     list(APPEND CURL_LIBS ${OPENSSL_LIBRARIES})
316     set(USE_OPENSSL ON)
317     set(HAVE_LIBCRYPTO ON)
318     set(HAVE_LIBSSL ON)
319     include_directories(${OPENSSL_INCLUDE_DIR})
320     set(CMAKE_REQUIRED_INCLUDES ${OPENSSL_INCLUDE_DIR})
321     check_include_file("openssl/crypto.h" HAVE_OPENSSL_CRYPTO_H)
322     check_include_file("openssl/engine.h" HAVE_OPENSSL_ENGINE_H)
323     check_include_file("openssl/err.h"    HAVE_OPENSSL_ERR_H)
324     check_include_file("openssl/pem.h"    HAVE_OPENSSL_PEM_H)
325     check_include_file("openssl/pkcs12.h" HAVE_OPENSSL_PKCS12_H)
326     check_include_file("openssl/rsa.h"    HAVE_OPENSSL_RSA_H)
327     check_include_file("openssl/ssl.h"    HAVE_OPENSSL_SSL_H)
328     check_include_file("openssl/x509.h"   HAVE_OPENSSL_X509_H)
329     check_include_file("openssl/rand.h"   HAVE_OPENSSL_RAND_H)
330   elseif(WIN32)
331     set(CURL_WINDOWS_SSPI ON)
332   endif()
333 endif()
334
335 option(USE_NGHTTP2 "Use Nghttp2 library" OFF)
336 if(USE_NGHTTP2)
337   find_package(NGHTTP2 REQUIRED)
338   include_directories(${NGHTTP2_INCLUDE_DIRS})
339   list(APPEND CURL_LIBS ${NGHTTP2_LIBRARIES})
340 endif()
341
342 if(NOT CURL_DISABLE_LDAP)
343   if(WIN32)
344     option(USE_WIN32_LDAP "Use Windows LDAP implementation" ON)
345     if(USE_WIN32_LDAP)
346       check_library_exists_concat("wldap32" cldap_open HAVE_WLDAP32)
347       if(NOT HAVE_WLDAP32)
348         set(USE_WIN32_LDAP OFF)
349       endif()
350     endif()
351   endif()
352
353   option(CMAKE_USE_OPENLDAP "Use OpenLDAP code." OFF)
354   mark_as_advanced(CMAKE_USE_OPENLDAP)
355   set(CMAKE_LDAP_LIB "ldap" CACHE STRING "Name or full path to ldap library")
356   set(CMAKE_LBER_LIB "lber" CACHE STRING "Name or full path to lber library")
357
358   if(CMAKE_USE_OPENLDAP AND USE_WIN32_LDAP)
359     message(FATAL_ERROR "Cannot use USE_WIN32_LDAP and CMAKE_USE_OPENLDAP at the same time")
360   endif()
361
362   # Now that we know, we're not using windows LDAP...
363   if(USE_WIN32_LDAP)
364     check_include_file_concat("winldap.h" HAVE_WINLDAP_H)
365     check_include_file_concat("winber.h"  HAVE_WINBER_H)
366   else()
367     # Check for LDAP
368     set(CMAKE_REQUIRED_LIBRARIES ${OPENSSL_LIBRARIES})
369     check_library_exists_concat(${CMAKE_LDAP_LIB} ldap_init HAVE_LIBLDAP)
370     check_library_exists_concat(${CMAKE_LBER_LIB} ber_init HAVE_LIBLBER)
371
372     set(CMAKE_REQUIRED_INCLUDES_BAK ${CMAKE_REQUIRED_INCLUDES})
373     set(CMAKE_LDAP_INCLUDE_DIR "" CACHE STRING "Path to LDAP include directory")
374     if(CMAKE_LDAP_INCLUDE_DIR)
375       list(APPEND CMAKE_REQUIRED_INCLUDES ${CMAKE_LDAP_INCLUDE_DIR})
376     endif()
377     check_include_file_concat("ldap.h"           HAVE_LDAP_H)
378     check_include_file_concat("lber.h"           HAVE_LBER_H)
379
380     if(NOT HAVE_LDAP_H)
381       message(STATUS "LDAP_H not found CURL_DISABLE_LDAP set ON")
382       set(CURL_DISABLE_LDAP ON CACHE BOOL "" FORCE)
383       set(CMAKE_REQUIRED_INCLUDES ${CMAKE_REQUIRED_INCLUDES_BAK}) #LDAP includes won't be used
384     elseif(NOT HAVE_LIBLDAP)
385       message(STATUS "LDAP library '${CMAKE_LDAP_LIB}' not found CURL_DISABLE_LDAP set ON")
386       set(CURL_DISABLE_LDAP ON CACHE BOOL "" FORCE)
387       set(CMAKE_REQUIRED_INCLUDES ${CMAKE_REQUIRED_INCLUDES_BAK}) #LDAP includes won't be used
388     else()
389       if(CMAKE_USE_OPENLDAP)
390         set(USE_OPENLDAP ON)
391       endif()
392       if(CMAKE_LDAP_INCLUDE_DIR)
393         include_directories(${CMAKE_LDAP_INCLUDE_DIR})
394       endif()
395       set(NEED_LBER_H ON)
396       set(_HEADER_LIST)
397       if(HAVE_WINDOWS_H)
398         list(APPEND _HEADER_LIST "windows.h")
399       endif()
400       if(HAVE_SYS_TYPES_H)
401         list(APPEND _HEADER_LIST "sys/types.h")
402       endif()
403       list(APPEND _HEADER_LIST "ldap.h")
404
405       set(_SRC_STRING "")
406       foreach(_HEADER ${_HEADER_LIST})
407         set(_INCLUDE_STRING "${_INCLUDE_STRING}#include <${_HEADER}>\n")
408       endforeach()
409
410       set(_SRC_STRING
411         "
412         ${_INCLUDE_STRING}
413         int main(int argc, char ** argv)
414         {
415           BerValue *bvp = NULL;
416           BerElement *bep = ber_init(bvp);
417           ber_free(bep, 1);
418           return 0;
419         }"
420       )
421       set(CMAKE_REQUIRED_DEFINITIONS "${CMAKE_REQUIRED_DEFINITIONS} -DLDAP_DEPRECATED=1")
422       list(APPEND CMAKE_REQUIRED_LIBRARIES ${CMAKE_LDAP_LIB})
423       if(HAVE_LIBLBER)
424         list(APPEND CMAKE_REQUIRED_LIBRARIES ${CMAKE_LBER_LIB})
425       endif()
426       check_c_source_compiles("${_SRC_STRING}" NOT_NEED_LBER_H)
427
428       if(NOT_NEED_LBER_H)
429         set(NEED_LBER_H OFF)
430       else()
431         set(CURL_TEST_DEFINES "${CURL_TEST_DEFINES} -DNEED_LBER_H")
432       endif()
433     endif()
434   endif()
435
436 endif()
437
438 # No ldap, no ldaps.
439 if(CURL_DISABLE_LDAP)
440   if(NOT CURL_DISABLE_LDAPS)
441     message(STATUS "LDAP needs to be enabled to support LDAPS")
442     set(CURL_DISABLE_LDAPS ON CACHE BOOL "" FORCE)
443   endif()
444 endif()
445
446 if(NOT CURL_DISABLE_LDAPS)
447   check_include_file_concat("ldap_ssl.h" HAVE_LDAP_SSL_H)
448   check_include_file_concat("ldapssl.h"  HAVE_LDAPSSL_H)
449 endif()
450
451 # Check for idn
452 check_library_exists_concat("idn2" idn2_lookup_ul HAVE_LIBIDN2)
453
454 # Check for symbol dlopen (same as HAVE_LIBDL)
455 check_library_exists("${CURL_LIBS}" dlopen "" HAVE_DLOPEN)
456
457 option(CURL_ZLIB "Set to ON to enable building curl with zlib support." ON)
458 set(HAVE_LIBZ OFF)
459 set(HAVE_ZLIB_H OFF)
460 set(HAVE_ZLIB OFF)
461 if(CURL_ZLIB)
462   find_package(ZLIB QUIET)
463   if(ZLIB_FOUND)
464     set(HAVE_ZLIB_H ON)
465     set(HAVE_ZLIB ON)
466     set(HAVE_LIBZ ON)
467     list(APPEND CURL_LIBS ${ZLIB_LIBRARIES})
468     include_directories(${ZLIB_INCLUDE_DIRS})
469     list(APPEND CMAKE_REQUIRED_INCLUDES ${ZLIB_INCLUDE_DIRS})
470   endif()
471 endif()
472
473 #libSSH2
474 option(CMAKE_USE_LIBSSH2 "Use libSSH2" ON)
475 mark_as_advanced(CMAKE_USE_LIBSSH2)
476 set(USE_LIBSSH2 OFF)
477 set(HAVE_LIBSSH2 OFF)
478 set(HAVE_LIBSSH2_H OFF)
479
480 if(CMAKE_USE_LIBSSH2)
481   find_package(LibSSH2)
482   if(LIBSSH2_FOUND)
483     list(APPEND CURL_LIBS ${LIBSSH2_LIBRARY})
484     set(CMAKE_REQUIRED_LIBRARIES ${LIBSSH2_LIBRARY})
485     list(APPEND CMAKE_REQUIRED_INCLUDES "${LIBSSH2_INCLUDE_DIR}")
486     include_directories("${LIBSSH2_INCLUDE_DIR}")
487     set(HAVE_LIBSSH2 ON)
488     set(USE_LIBSSH2 ON)
489
490     # find_package has already found the headers
491     set(HAVE_LIBSSH2_H ON)
492     set(CURL_INCLUDES ${CURL_INCLUDES} "${LIBSSH2_INCLUDE_DIR}/libssh2.h")
493     set(CURL_TEST_DEFINES "${CURL_TEST_DEFINES} -DHAVE_LIBSSH2_H")
494
495     # now check for specific libssh2 symbols as they were added in different versions
496     set(CMAKE_EXTRA_INCLUDE_FILES "libssh2.h")
497     check_function_exists(libssh2_version           HAVE_LIBSSH2_VERSION)
498     check_function_exists(libssh2_init              HAVE_LIBSSH2_INIT)
499     check_function_exists(libssh2_exit              HAVE_LIBSSH2_EXIT)
500     check_function_exists(libssh2_scp_send64        HAVE_LIBSSH2_SCP_SEND64)
501     check_function_exists(libssh2_session_handshake HAVE_LIBSSH2_SESSION_HANDSHAKE)
502     set(CMAKE_EXTRA_INCLUDE_FILES "")
503
504   endif(LIBSSH2_FOUND)
505 endif(CMAKE_USE_LIBSSH2)
506
507 option(CMAKE_USE_GSSAPI "Use GSSAPI implementation (right now only Heimdal is supported with CMake build)" OFF)
508 mark_as_advanced(CMAKE_USE_GSSAPI)
509
510 if(CMAKE_USE_GSSAPI)
511   find_package(GSS)
512
513   set(HAVE_GSSAPI ${GSS_FOUND})
514   if(GSS_FOUND)
515
516     message(STATUS "Found ${GSS_FLAVOUR} GSSAPI version: \"${GSS_VERSION}\"")
517
518     list(APPEND CMAKE_REQUIRED_INCLUDES ${GSS_INCLUDE_DIRECTORIES})
519     check_include_file_concat("gssapi/gssapi.h"  HAVE_GSSAPI_GSSAPI_H)
520     check_include_file_concat("gssapi/gssapi_generic.h" HAVE_GSSAPI_GSSAPI_GENERIC_H)
521     check_include_file_concat("gssapi/gssapi_krb5.h" HAVE_GSSAPI_GSSAPI_KRB5_H)
522
523     if(GSS_FLAVOUR STREQUAL "Heimdal")
524       set(HAVE_GSSHEIMDAL ON)
525     else() # MIT
526       set(HAVE_GSSMIT ON)
527       set(_INCLUDE_LIST "")
528       if(HAVE_GSSAPI_GSSAPI_H)
529         list(APPEND _INCLUDE_LIST "gssapi/gssapi.h")
530       endif()
531       if(HAVE_GSSAPI_GSSAPI_GENERIC_H)
532         list(APPEND _INCLUDE_LIST "gssapi/gssapi_generic.h")
533       endif()
534       if(HAVE_GSSAPI_GSSAPI_KRB5_H)
535         list(APPEND _INCLUDE_LIST "gssapi/gssapi_krb5.h")
536       endif()
537
538       string(REPLACE ";" " " _COMPILER_FLAGS_STR "${GSS_COMPILER_FLAGS}")
539       string(REPLACE ";" " " _LINKER_FLAGS_STR "${GSS_LINKER_FLAGS}")
540
541       foreach(_dir ${GSS_LINK_DIRECTORIES})
542         set(_LINKER_FLAGS_STR "${_LINKER_FLAGS_STR} -L\"${_dir}\"")
543       endforeach()
544
545       set(CMAKE_REQUIRED_FLAGS "${_COMPILER_FLAGS_STR} ${_LINKER_FLAGS_STR}")
546       set(CMAKE_REQUIRED_LIBRARIES ${GSS_LIBRARIES})
547       check_symbol_exists("GSS_C_NT_HOSTBASED_SERVICE" ${_INCLUDE_LIST} HAVE_GSS_C_NT_HOSTBASED_SERVICE)
548       if(NOT HAVE_GSS_C_NT_HOSTBASED_SERVICE)
549         set(HAVE_OLD_GSSMIT ON)
550       endif()
551
552     endif()
553
554     include_directories(${GSS_INCLUDE_DIRECTORIES})
555     link_directories(${GSS_LINK_DIRECTORIES})
556     set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${GSS_COMPILER_FLAGS}")
557     set(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} ${GSS_LINKER_FLAGS}")
558     set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} ${GSS_LINKER_FLAGS}")
559     list(APPEND CURL_LIBS ${GSS_LIBRARIES})
560
561   else()
562     message(WARNING "GSSAPI support has been requested but no supporting libraries found. Skipping.")
563   endif()
564 endif()
565
566 option(ENABLE_UNIX_SOCKETS "Define if you want Unix domain sockets support" ON)
567 if(ENABLE_UNIX_SOCKETS)
568   include(CheckStructHasMember)
569   check_struct_has_member("struct sockaddr_un" sun_path "sys/un.h" USE_UNIX_SOCKETS)
570 else()
571   unset(USE_UNIX_SOCKETS CACHE)
572 endif()
573
574
575 # Check for header files
576 if(NOT UNIX)
577   check_include_file_concat("windows.h"      HAVE_WINDOWS_H)
578   check_include_file_concat("winsock.h"      HAVE_WINSOCK_H)
579   check_include_file_concat("ws2tcpip.h"     HAVE_WS2TCPIP_H)
580   check_include_file_concat("winsock2.h"     HAVE_WINSOCK2_H)
581   if(CURL_WINDOWS_SSPI)
582     set(CMAKE_REQUIRED_DEFINITIONS "${CMAKE_REQUIRED_DEFINITIONS} -DSECURITY_WIN32")
583     check_include_file_concat("sspi.h"       HAVE_SSPI_H)
584     if(HAVE_SSPI_H)
585       check_include_file_concat("schannel.h" HAVE_SCHANNEL_H)
586       set(USE_WINDOWS_SSPI ON)
587       if(HAVE_SCHANNEL_H)
588         set(USE_SCHANNEL ON)
589         set(SSL_ENABLED ON)
590         set(CURL_LIBS ${CURL_LIBS} "crypt32")
591       endif()
592     endif()
593   elseif(USE_OPENSSL)
594     set(CURL_LIBS ${CURL_LIBS} "crypt32")
595   endif()
596 endif(NOT UNIX)
597
598 check_include_file_concat("stdio.h"          HAVE_STDIO_H)
599 check_include_file_concat("inttypes.h"       HAVE_INTTYPES_H)
600 check_include_file_concat("sys/filio.h"      HAVE_SYS_FILIO_H)
601 check_include_file_concat("sys/ioctl.h"      HAVE_SYS_IOCTL_H)
602 check_include_file_concat("sys/param.h"      HAVE_SYS_PARAM_H)
603 check_include_file_concat("sys/poll.h"       HAVE_SYS_POLL_H)
604 check_include_file_concat("sys/resource.h"   HAVE_SYS_RESOURCE_H)
605 check_include_file_concat("sys/select.h"     HAVE_SYS_SELECT_H)
606 check_include_file_concat("sys/socket.h"     HAVE_SYS_SOCKET_H)
607 check_include_file_concat("sys/sockio.h"     HAVE_SYS_SOCKIO_H)
608 check_include_file_concat("sys/stat.h"       HAVE_SYS_STAT_H)
609 check_include_file_concat("sys/time.h"       HAVE_SYS_TIME_H)
610 check_include_file_concat("sys/types.h"      HAVE_SYS_TYPES_H)
611 check_include_file_concat("sys/uio.h"        HAVE_SYS_UIO_H)
612 check_include_file_concat("sys/un.h"         HAVE_SYS_UN_H)
613 check_include_file_concat("sys/utime.h"      HAVE_SYS_UTIME_H)
614 check_include_file_concat("sys/xattr.h"      HAVE_SYS_XATTR_H)
615 check_include_file_concat("alloca.h"         HAVE_ALLOCA_H)
616 check_include_file_concat("arpa/inet.h"      HAVE_ARPA_INET_H)
617 check_include_file_concat("arpa/tftp.h"      HAVE_ARPA_TFTP_H)
618 check_include_file_concat("assert.h"         HAVE_ASSERT_H)
619 check_include_file_concat("crypto.h"         HAVE_CRYPTO_H)
620 check_include_file_concat("des.h"            HAVE_DES_H)
621 check_include_file_concat("err.h"            HAVE_ERR_H)
622 check_include_file_concat("errno.h"          HAVE_ERRNO_H)
623 check_include_file_concat("fcntl.h"          HAVE_FCNTL_H)
624 check_include_file_concat("idn2.h"           HAVE_IDN2_H)
625 check_include_file_concat("ifaddrs.h"        HAVE_IFADDRS_H)
626 check_include_file_concat("io.h"             HAVE_IO_H)
627 check_include_file_concat("krb.h"            HAVE_KRB_H)
628 check_include_file_concat("libgen.h"         HAVE_LIBGEN_H)
629 check_include_file_concat("limits.h"         HAVE_LIMITS_H)
630 check_include_file_concat("locale.h"         HAVE_LOCALE_H)
631 check_include_file_concat("net/if.h"         HAVE_NET_IF_H)
632 check_include_file_concat("netdb.h"          HAVE_NETDB_H)
633 check_include_file_concat("netinet/in.h"     HAVE_NETINET_IN_H)
634 check_include_file_concat("netinet/tcp.h"    HAVE_NETINET_TCP_H)
635
636 check_include_file_concat("pem.h"            HAVE_PEM_H)
637 check_include_file_concat("poll.h"           HAVE_POLL_H)
638 check_include_file_concat("pwd.h"            HAVE_PWD_H)
639 check_include_file_concat("rsa.h"            HAVE_RSA_H)
640 check_include_file_concat("setjmp.h"         HAVE_SETJMP_H)
641 check_include_file_concat("sgtty.h"          HAVE_SGTTY_H)
642 check_include_file_concat("signal.h"         HAVE_SIGNAL_H)
643 check_include_file_concat("ssl.h"            HAVE_SSL_H)
644 check_include_file_concat("stdbool.h"        HAVE_STDBOOL_H)
645 check_include_file_concat("stdint.h"         HAVE_STDINT_H)
646 check_include_file_concat("stdio.h"          HAVE_STDIO_H)
647 check_include_file_concat("stdlib.h"         HAVE_STDLIB_H)
648 check_include_file_concat("string.h"         HAVE_STRING_H)
649 check_include_file_concat("strings.h"        HAVE_STRINGS_H)
650 check_include_file_concat("stropts.h"        HAVE_STROPTS_H)
651 check_include_file_concat("termio.h"         HAVE_TERMIO_H)
652 check_include_file_concat("termios.h"        HAVE_TERMIOS_H)
653 check_include_file_concat("time.h"           HAVE_TIME_H)
654 check_include_file_concat("unistd.h"         HAVE_UNISTD_H)
655 check_include_file_concat("utime.h"          HAVE_UTIME_H)
656 check_include_file_concat("x509.h"           HAVE_X509_H)
657
658 check_include_file_concat("process.h"        HAVE_PROCESS_H)
659 check_include_file_concat("stddef.h"         HAVE_STDDEF_H)
660 check_include_file_concat("dlfcn.h"          HAVE_DLFCN_H)
661 check_include_file_concat("malloc.h"         HAVE_MALLOC_H)
662 check_include_file_concat("memory.h"         HAVE_MEMORY_H)
663 check_include_file_concat("netinet/if_ether.h" HAVE_NETINET_IF_ETHER_H)
664 check_include_file_concat("stdint.h"        HAVE_STDINT_H)
665 check_include_file_concat("sockio.h"        HAVE_SOCKIO_H)
666 check_include_file_concat("sys/utsname.h"   HAVE_SYS_UTSNAME_H)
667
668 check_type_size(size_t  SIZEOF_SIZE_T)
669 check_type_size(ssize_t  SIZEOF_SSIZE_T)
670 check_type_size("long long"  SIZEOF_LONG_LONG)
671 check_type_size("long"  SIZEOF_LONG)
672 check_type_size("short"  SIZEOF_SHORT)
673 check_type_size("int"  SIZEOF_INT)
674 check_type_size("__int64"  SIZEOF___INT64)
675 check_type_size("long double"  SIZEOF_LONG_DOUBLE)
676 check_type_size("time_t"  SIZEOF_TIME_T)
677 if(NOT HAVE_SIZEOF_SSIZE_T)
678   if(SIZEOF_LONG EQUAL SIZEOF_SIZE_T)
679     set(ssize_t long)
680   endif(SIZEOF_LONG EQUAL SIZEOF_SIZE_T)
681   if(NOT ssize_t AND SIZEOF___INT64 EQUAL SIZEOF_SIZE_T)
682     set(ssize_t __int64)
683   endif(NOT ssize_t AND SIZEOF___INT64 EQUAL SIZEOF_SIZE_T)
684 endif(NOT HAVE_SIZEOF_SSIZE_T)
685 # off_t is sized later, after the HAVE_FILE_OFFSET_BITS test
686
687 # Different sizeofs, etc.
688
689 #    define CURL_SIZEOF_LONG        4
690 #    define CURL_TYPEOF_CURL_OFF_T  long long
691 #    define CURL_FORMAT_CURL_OFF_T  "lld"
692 #    define CURL_FORMAT_CURL_OFF_TU "llu"
693 #    define CURL_FORMAT_OFF_T       "%lld"
694 #    define CURL_SIZEOF_CURL_OFF_T  8
695 #    define CURL_SUFFIX_CURL_OFF_T  LL
696 #    define CURL_SUFFIX_CURL_OFF_TU ULL
697
698 set(CURL_SIZEOF_LONG ${SIZEOF_LONG})
699
700 if(SIZEOF_LONG EQUAL 8)
701   set(CURL_TYPEOF_CURL_OFF_T long)
702   set(CURL_SIZEOF_CURL_OFF_T 8)
703   set(CURL_FORMAT_CURL_OFF_T "ld")
704   set(CURL_FORMAT_CURL_OFF_TU "lu")
705   set(CURL_FORMAT_OFF_T "%ld")
706   set(CURL_SUFFIX_CURL_OFF_T L)
707   set(CURL_SUFFIX_CURL_OFF_TU UL)
708 endif(SIZEOF_LONG EQUAL 8)
709
710 if(SIZEOF_LONG_LONG EQUAL 8)
711   set(CURL_TYPEOF_CURL_OFF_T "long long")
712   set(CURL_SIZEOF_CURL_OFF_T 8)
713   set(CURL_FORMAT_CURL_OFF_T "lld")
714   set(CURL_FORMAT_CURL_OFF_TU "llu")
715   set(CURL_FORMAT_OFF_T "%lld")
716   set(CURL_SUFFIX_CURL_OFF_T LL)
717   set(CURL_SUFFIX_CURL_OFF_TU ULL)
718 endif(SIZEOF_LONG_LONG EQUAL 8)
719
720 if(NOT CURL_TYPEOF_CURL_OFF_T)
721   set(CURL_TYPEOF_CURL_OFF_T ${ssize_t})
722   set(CURL_SIZEOF_CURL_OFF_T ${SIZEOF_SSIZE_T})
723   # TODO: need adjustment here.
724   set(CURL_FORMAT_CURL_OFF_T "ld")
725   set(CURL_FORMAT_CURL_OFF_TU "lu")
726   set(CURL_FORMAT_OFF_T "%ld")
727   set(CURL_SUFFIX_CURL_OFF_T L)
728   set(CURL_SUFFIX_CURL_OFF_TU LU)
729 endif(NOT CURL_TYPEOF_CURL_OFF_T)
730
731 if(HAVE_SIZEOF_LONG_LONG)
732   set(HAVE_LONGLONG 1)
733   set(HAVE_LL 1)
734 endif(HAVE_SIZEOF_LONG_LONG)
735
736 find_file(RANDOM_FILE urandom /dev)
737 mark_as_advanced(RANDOM_FILE)
738
739 # Check for some functions that are used
740 if(HAVE_LIBWS2_32)
741   set(CMAKE_REQUIRED_LIBRARIES ws2_32)
742 elseif(HAVE_LIBSOCKET)
743   set(CMAKE_REQUIRED_LIBRARIES socket)
744 endif()
745
746 check_symbol_exists(basename      "${CURL_INCLUDES}" HAVE_BASENAME)
747 check_symbol_exists(socket        "${CURL_INCLUDES}" HAVE_SOCKET)
748 # poll on macOS is unreliable, it first did not exist, then was broken until
749 # fixed in 10.9 only to break again in 10.12.
750 if(NOT APPLE)
751   check_symbol_exists(poll        "${CURL_INCLUDES}" HAVE_POLL)
752 endif()
753 check_symbol_exists(select        "${CURL_INCLUDES}" HAVE_SELECT)
754 check_symbol_exists(strdup        "${CURL_INCLUDES}" HAVE_STRDUP)
755 check_symbol_exists(strstr        "${CURL_INCLUDES}" HAVE_STRSTR)
756 check_symbol_exists(strtok_r      "${CURL_INCLUDES}" HAVE_STRTOK_R)
757 check_symbol_exists(strftime      "${CURL_INCLUDES}" HAVE_STRFTIME)
758 check_symbol_exists(uname         "${CURL_INCLUDES}" HAVE_UNAME)
759 check_symbol_exists(strcasecmp    "${CURL_INCLUDES}" HAVE_STRCASECMP)
760 check_symbol_exists(stricmp       "${CURL_INCLUDES}" HAVE_STRICMP)
761 check_symbol_exists(strcmpi       "${CURL_INCLUDES}" HAVE_STRCMPI)
762 check_symbol_exists(strncmpi      "${CURL_INCLUDES}" HAVE_STRNCMPI)
763 check_symbol_exists(alarm         "${CURL_INCLUDES}" HAVE_ALARM)
764 if(NOT HAVE_STRNCMPI)
765   set(HAVE_STRCMPI)
766 endif(NOT HAVE_STRNCMPI)
767 check_symbol_exists(gethostbyaddr "${CURL_INCLUDES}" HAVE_GETHOSTBYADDR)
768 check_symbol_exists(gethostbyaddr_r "${CURL_INCLUDES}" HAVE_GETHOSTBYADDR_R)
769 check_symbol_exists(gettimeofday  "${CURL_INCLUDES}" HAVE_GETTIMEOFDAY)
770 check_symbol_exists(inet_addr     "${CURL_INCLUDES}" HAVE_INET_ADDR)
771 check_symbol_exists(inet_ntoa     "${CURL_INCLUDES}" HAVE_INET_NTOA)
772 check_symbol_exists(inet_ntoa_r   "${CURL_INCLUDES}" HAVE_INET_NTOA_R)
773 check_symbol_exists(tcsetattr     "${CURL_INCLUDES}" HAVE_TCSETATTR)
774 check_symbol_exists(tcgetattr     "${CURL_INCLUDES}" HAVE_TCGETATTR)
775 check_symbol_exists(perror        "${CURL_INCLUDES}" HAVE_PERROR)
776 check_symbol_exists(closesocket   "${CURL_INCLUDES}" HAVE_CLOSESOCKET)
777 check_symbol_exists(setvbuf       "${CURL_INCLUDES}" HAVE_SETVBUF)
778 check_symbol_exists(sigsetjmp     "${CURL_INCLUDES}" HAVE_SIGSETJMP)
779 check_symbol_exists(getpass_r     "${CURL_INCLUDES}" HAVE_GETPASS_R)
780 check_symbol_exists(strlcat       "${CURL_INCLUDES}" HAVE_STRLCAT)
781 check_symbol_exists(getpwuid      "${CURL_INCLUDES}" HAVE_GETPWUID)
782 check_symbol_exists(geteuid       "${CURL_INCLUDES}" HAVE_GETEUID)
783 check_symbol_exists(utime         "${CURL_INCLUDES}" HAVE_UTIME)
784 if(CMAKE_USE_OPENSSL)
785   check_symbol_exists(RAND_status   "${CURL_INCLUDES}" HAVE_RAND_STATUS)
786   check_symbol_exists(RAND_screen   "${CURL_INCLUDES}" HAVE_RAND_SCREEN)
787   check_symbol_exists(RAND_egd      "${CURL_INCLUDES}" HAVE_RAND_EGD)
788   if(HAVE_LIBCRYPTO AND HAVE_LIBSSL)
789     set(USE_OPENSSL 1)
790   endif(HAVE_LIBCRYPTO AND HAVE_LIBSSL)
791 endif(CMAKE_USE_OPENSSL)
792 check_symbol_exists(gmtime_r      "${CURL_INCLUDES}" HAVE_GMTIME_R)
793 check_symbol_exists(localtime_r   "${CURL_INCLUDES}" HAVE_LOCALTIME_R)
794
795 check_symbol_exists(gethostbyname   "${CURL_INCLUDES}" HAVE_GETHOSTBYNAME)
796 check_symbol_exists(gethostbyname_r "${CURL_INCLUDES}" HAVE_GETHOSTBYNAME_R)
797
798 check_symbol_exists(signal        "${CURL_INCLUDES}" HAVE_SIGNAL_FUNC)
799 check_symbol_exists(SIGALRM       "${CURL_INCLUDES}" HAVE_SIGNAL_MACRO)
800 if(HAVE_SIGNAL_FUNC AND HAVE_SIGNAL_MACRO)
801   set(HAVE_SIGNAL 1)
802 endif(HAVE_SIGNAL_FUNC AND HAVE_SIGNAL_MACRO)
803 check_symbol_exists(uname          "${CURL_INCLUDES}" HAVE_UNAME)
804 check_symbol_exists(strtoll        "${CURL_INCLUDES}" HAVE_STRTOLL)
805 check_symbol_exists(_strtoi64      "${CURL_INCLUDES}" HAVE__STRTOI64)
806 check_symbol_exists(strerror_r     "${CURL_INCLUDES}" HAVE_STRERROR_R)
807 check_symbol_exists(siginterrupt   "${CURL_INCLUDES}" HAVE_SIGINTERRUPT)
808 check_symbol_exists(perror         "${CURL_INCLUDES}" HAVE_PERROR)
809 check_symbol_exists(fork           "${CURL_INCLUDES}" HAVE_FORK)
810 check_symbol_exists(getaddrinfo    "${CURL_INCLUDES}" HAVE_GETADDRINFO)
811 check_symbol_exists(freeaddrinfo   "${CURL_INCLUDES}" HAVE_FREEADDRINFO)
812 check_symbol_exists(freeifaddrs    "${CURL_INCLUDES}" HAVE_FREEIFADDRS)
813 check_symbol_exists(pipe           "${CURL_INCLUDES}" HAVE_PIPE)
814 check_symbol_exists(ftruncate      "${CURL_INCLUDES}" HAVE_FTRUNCATE)
815 check_symbol_exists(getprotobyname "${CURL_INCLUDES}" HAVE_GETPROTOBYNAME)
816 check_symbol_exists(getrlimit      "${CURL_INCLUDES}" HAVE_GETRLIMIT)
817 check_symbol_exists(setlocale      "${CURL_INCLUDES}" HAVE_SETLOCALE)
818 check_symbol_exists(setrlimit      "${CURL_INCLUDES}" HAVE_SETRLIMIT)
819 check_symbol_exists(fcntl          "${CURL_INCLUDES}" HAVE_FCNTL)
820 check_symbol_exists(ioctl          "${CURL_INCLUDES}" HAVE_IOCTL)
821 check_symbol_exists(setsockopt     "${CURL_INCLUDES}" HAVE_SETSOCKOPT)
822
823 # symbol exists in win32, but function does not.
824 check_function_exists(inet_pton HAVE_INET_PTON)
825
826 check_symbol_exists(fsetxattr "${CURL_INCLUDES}" HAVE_FSETXATTR)
827 if(HAVE_FSETXATTR)
828   foreach(CURL_TEST HAVE_FSETXATTR_5 HAVE_FSETXATTR_6)
829     curl_internal_test_run(${CURL_TEST})
830   endforeach(CURL_TEST)
831 endif(HAVE_FSETXATTR)
832
833 # sigaction and sigsetjmp are special. Use special mechanism for
834 # detecting those, but only if previous attempt failed.
835 if(HAVE_SIGNAL_H)
836   check_symbol_exists(sigaction "signal.h" HAVE_SIGACTION)
837 endif(HAVE_SIGNAL_H)
838
839 if(NOT HAVE_SIGSETJMP)
840   if(HAVE_SETJMP_H)
841     check_symbol_exists(sigsetjmp "setjmp.h" HAVE_MACRO_SIGSETJMP)
842     if(HAVE_MACRO_SIGSETJMP)
843       set(HAVE_SIGSETJMP 1)
844     endif(HAVE_MACRO_SIGSETJMP)
845   endif(HAVE_SETJMP_H)
846 endif(NOT HAVE_SIGSETJMP)
847
848 # If there is no stricmp(), do not allow LDAP to parse URLs
849 if(NOT HAVE_STRICMP)
850   set(HAVE_LDAP_URL_PARSE 1)
851 endif(NOT HAVE_STRICMP)
852
853 # Do curl specific tests
854 foreach(CURL_TEST
855     HAVE_FCNTL_O_NONBLOCK
856     HAVE_IOCTLSOCKET
857     HAVE_IOCTLSOCKET_CAMEL
858     HAVE_IOCTLSOCKET_CAMEL_FIONBIO
859     HAVE_IOCTLSOCKET_FIONBIO
860     HAVE_IOCTL_FIONBIO
861     HAVE_IOCTL_SIOCGIFADDR
862     HAVE_SETSOCKOPT_SO_NONBLOCK
863     HAVE_SOCKADDR_IN6_SIN6_SCOPE_ID
864     TIME_WITH_SYS_TIME
865     HAVE_O_NONBLOCK
866     HAVE_GETHOSTBYADDR_R_5
867     HAVE_GETHOSTBYADDR_R_7
868     HAVE_GETHOSTBYADDR_R_8
869     HAVE_GETHOSTBYADDR_R_5_REENTRANT
870     HAVE_GETHOSTBYADDR_R_7_REENTRANT
871     HAVE_GETHOSTBYADDR_R_8_REENTRANT
872     HAVE_GETHOSTBYNAME_R_3
873     HAVE_GETHOSTBYNAME_R_5
874     HAVE_GETHOSTBYNAME_R_6
875     HAVE_GETHOSTBYNAME_R_3_REENTRANT
876     HAVE_GETHOSTBYNAME_R_5_REENTRANT
877     HAVE_GETHOSTBYNAME_R_6_REENTRANT
878     HAVE_SOCKLEN_T
879     HAVE_IN_ADDR_T
880     HAVE_BOOL_T
881     STDC_HEADERS
882     RETSIGTYPE_TEST
883     HAVE_INET_NTOA_R_DECL
884     HAVE_INET_NTOA_R_DECL_REENTRANT
885     HAVE_GETADDRINFO
886     HAVE_FILE_OFFSET_BITS
887     )
888   curl_internal_test(${CURL_TEST})
889 endforeach(CURL_TEST)
890
891 if(HAVE_FILE_OFFSET_BITS)
892   set(_FILE_OFFSET_BITS 64)
893   set(CMAKE_REQUIRED_FLAGS "-D_FILE_OFFSET_BITS=64")
894 endif(HAVE_FILE_OFFSET_BITS)
895 check_type_size("off_t"  SIZEOF_OFF_T)
896 set(CMAKE_REQUIRED_FLAGS)
897
898 foreach(CURL_TEST
899     HAVE_GLIBC_STRERROR_R
900     HAVE_POSIX_STRERROR_R
901     )
902   curl_internal_test_run(${CURL_TEST})
903 endforeach(CURL_TEST)
904
905 # Check for reentrant
906 foreach(CURL_TEST
907     HAVE_GETHOSTBYADDR_R_5
908     HAVE_GETHOSTBYADDR_R_7
909     HAVE_GETHOSTBYADDR_R_8
910     HAVE_GETHOSTBYNAME_R_3
911     HAVE_GETHOSTBYNAME_R_5
912     HAVE_GETHOSTBYNAME_R_6
913     HAVE_INET_NTOA_R_DECL_REENTRANT)
914   if(NOT ${CURL_TEST})
915     if(${CURL_TEST}_REENTRANT)
916       set(NEED_REENTRANT 1)
917     endif(${CURL_TEST}_REENTRANT)
918   endif(NOT ${CURL_TEST})
919 endforeach(CURL_TEST)
920
921 if(NEED_REENTRANT)
922   foreach(CURL_TEST
923       HAVE_GETHOSTBYADDR_R_5
924       HAVE_GETHOSTBYADDR_R_7
925       HAVE_GETHOSTBYADDR_R_8
926       HAVE_GETHOSTBYNAME_R_3
927       HAVE_GETHOSTBYNAME_R_5
928       HAVE_GETHOSTBYNAME_R_6)
929     set(${CURL_TEST} 0)
930     if(${CURL_TEST}_REENTRANT)
931       set(${CURL_TEST} 1)
932     endif(${CURL_TEST}_REENTRANT)
933   endforeach(CURL_TEST)
934 endif(NEED_REENTRANT)
935
936 if(HAVE_INET_NTOA_R_DECL_REENTRANT)
937   set(HAVE_INET_NTOA_R_DECL 1)
938   set(NEED_REENTRANT 1)
939 endif(HAVE_INET_NTOA_R_DECL_REENTRANT)
940
941 # Some other minor tests
942
943 if(NOT HAVE_IN_ADDR_T)
944   set(in_addr_t "unsigned long")
945 endif(NOT HAVE_IN_ADDR_T)
946
947 # Fix libz / zlib.h
948
949 if(NOT CURL_SPECIAL_LIBZ)
950   if(NOT HAVE_LIBZ)
951     set(HAVE_ZLIB_H 0)
952   endif(NOT HAVE_LIBZ)
953
954   if(NOT HAVE_ZLIB_H)
955     set(HAVE_LIBZ 0)
956   endif(NOT HAVE_ZLIB_H)
957 endif(NOT CURL_SPECIAL_LIBZ)
958
959 # Check for nonblocking
960 set(HAVE_DISABLED_NONBLOCKING 1)
961 if(HAVE_FIONBIO OR
962     HAVE_IOCTLSOCKET OR
963     HAVE_IOCTLSOCKET_CASE OR
964     HAVE_O_NONBLOCK)
965   set(HAVE_DISABLED_NONBLOCKING)
966 endif(HAVE_FIONBIO OR
967   HAVE_IOCTLSOCKET OR
968   HAVE_IOCTLSOCKET_CASE OR
969   HAVE_O_NONBLOCK)
970
971 if(RETSIGTYPE_TEST)
972   set(RETSIGTYPE void)
973 else(RETSIGTYPE_TEST)
974   set(RETSIGTYPE int)
975 endif(RETSIGTYPE_TEST)
976
977 if(CMAKE_COMPILER_IS_GNUCC AND APPLE)
978   include(CheckCCompilerFlag)
979   check_c_compiler_flag(-Wno-long-double HAVE_C_FLAG_Wno_long_double)
980   if(HAVE_C_FLAG_Wno_long_double)
981     # The Mac version of GCC warns about use of long double.  Disable it.
982     get_source_file_property(MPRINTF_COMPILE_FLAGS mprintf.c COMPILE_FLAGS)
983     if(MPRINTF_COMPILE_FLAGS)
984       set(MPRINTF_COMPILE_FLAGS "${MPRINTF_COMPILE_FLAGS} -Wno-long-double")
985     else(MPRINTF_COMPILE_FLAGS)
986       set(MPRINTF_COMPILE_FLAGS "-Wno-long-double")
987     endif(MPRINTF_COMPILE_FLAGS)
988     set_source_files_properties(mprintf.c PROPERTIES
989       COMPILE_FLAGS ${MPRINTF_COMPILE_FLAGS})
990   endif(HAVE_C_FLAG_Wno_long_double)
991 endif(CMAKE_COMPILER_IS_GNUCC AND APPLE)
992
993 if(HAVE_SOCKLEN_T)
994   set(CURL_TYPEOF_CURL_SOCKLEN_T "socklen_t")
995   if(WIN32)
996     set(CMAKE_EXTRA_INCLUDE_FILES "winsock2.h;ws2tcpip.h")
997   elseif(HAVE_SYS_SOCKET_H)
998     set(CMAKE_EXTRA_INCLUDE_FILES "sys/socket.h")
999   endif()
1000   check_type_size("socklen_t" CURL_SIZEOF_CURL_SOCKLEN_T)
1001   set(CMAKE_EXTRA_INCLUDE_FILES)
1002   if(NOT HAVE_CURL_SIZEOF_CURL_SOCKLEN_T)
1003     message(FATAL_ERROR
1004      "Check for sizeof socklen_t failed, see CMakeFiles/CMakerror.log")
1005   endif()
1006 else()
1007   set(CURL_TYPEOF_CURL_SOCKLEN_T int)
1008   set(CURL_SIZEOF_CURL_SOCKLEN_T ${SIZEOF_INT})
1009 endif()
1010
1011 # TODO test which of these headers are required for the typedefs used in curlbuild.h
1012 if(WIN32)
1013   set(CURL_PULL_WS2TCPIP_H ${HAVE_WS2TCPIP_H})
1014 else()
1015   set(CURL_PULL_SYS_TYPES_H ${HAVE_SYS_TYPES_H})
1016   set(CURL_PULL_SYS_SOCKET_H ${HAVE_SYS_SOCKET_H})
1017   set(CURL_PULL_SYS_POLL_H ${HAVE_SYS_POLL_H})
1018 endif()
1019 set(CURL_PULL_STDINT_H ${HAVE_STDINT_H})
1020 set(CURL_PULL_INTTYPES_H ${HAVE_INTTYPES_H})
1021
1022 include(CMake/OtherTests.cmake)
1023
1024 add_definitions(-DHAVE_CONFIG_H)
1025
1026 # For windows, do not allow the compiler to use default target (Vista).
1027 if(WIN32)
1028   add_definitions(-D_WIN32_WINNT=0x0501)
1029 endif(WIN32)
1030
1031 # For windows, all compilers used by cmake should support large files
1032 if(WIN32)
1033   set(USE_WIN32_LARGE_FILES ON)
1034 endif(WIN32)
1035
1036 if(MSVC)
1037   add_definitions(-D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE)
1038 endif(MSVC)
1039
1040 # Ugly (but functional) way to include "Makefile.inc" by transforming it (= regenerate it).
1041 function(TRANSFORM_MAKEFILE_INC INPUT_FILE OUTPUT_FILE)
1042   file(READ ${INPUT_FILE} MAKEFILE_INC_TEXT)
1043   string(REPLACE "$(top_srcdir)"   "\${CURL_SOURCE_DIR}" MAKEFILE_INC_TEXT ${MAKEFILE_INC_TEXT})
1044   string(REPLACE "$(top_builddir)" "\${CURL_BINARY_DIR}" MAKEFILE_INC_TEXT ${MAKEFILE_INC_TEXT})
1045
1046   string(REGEX REPLACE "\\\\\n" "§!§" MAKEFILE_INC_TEXT ${MAKEFILE_INC_TEXT})
1047   string(REGEX REPLACE "([a-zA-Z_][a-zA-Z0-9_]*)[\t ]*=[\t ]*([^\n]*)" "SET(\\1 \\2)" MAKEFILE_INC_TEXT ${MAKEFILE_INC_TEXT})
1048   string(REPLACE "§!§" "\n" MAKEFILE_INC_TEXT ${MAKEFILE_INC_TEXT})
1049
1050   string(REGEX REPLACE "\\$\\(([a-zA-Z_][a-zA-Z0-9_]*)\\)" "\${\\1}" MAKEFILE_INC_TEXT ${MAKEFILE_INC_TEXT})    # Replace $() with ${}
1051   string(REGEX REPLACE "@([a-zA-Z_][a-zA-Z0-9_]*)@" "\${\\1}" MAKEFILE_INC_TEXT ${MAKEFILE_INC_TEXT})    # Replace @@ with ${}, even if that may not be read by CMake scripts.
1052   file(WRITE ${OUTPUT_FILE} ${MAKEFILE_INC_TEXT})
1053
1054 endfunction()
1055
1056 add_subdirectory(lib)
1057 if(BUILD_CURL_EXE)
1058   add_subdirectory(src)
1059 endif()
1060
1061 include(CTest)
1062 if(BUILD_TESTING)
1063   add_subdirectory(tests)
1064 endif()
1065
1066 # TODO support GNUTLS, NSS, POLARSSL, AXTLS, CYASSL, WINSSL, DARWINSSL
1067 if(USE_OPENSSL)
1068   set(SSL_ENABLED 1)
1069 endif()
1070
1071 # Helper to populate a list (_items) with a label when conditions (the remaining
1072 # args) are satisfied
1073 function(_add_if label)
1074   # TODO need to disable policy CMP0054 (CMake 3.1) to allow this indirection
1075   if(${ARGN})
1076     set(_items ${_items} "${label}" PARENT_SCOPE)
1077   endif()
1078 endfunction()
1079
1080 # Clear list and try to detect available features
1081 set(_items)
1082 _add_if("WinSSL"        SSL_ENABLED AND USE_WINDOWS_SSPI)
1083 _add_if("OpenSSL"       SSL_ENABLED AND USE_OPENSSL)
1084 _add_if("IPv6"          ENABLE_IPV6)
1085 _add_if("unix-sockets"  USE_UNIX_SOCKETS)
1086 _add_if("libz"          HAVE_LIBZ)
1087 _add_if("AsynchDNS"     USE_ARES OR USE_THREADS_POSIX OR USE_THREADS_WIN32)
1088 _add_if("IDN"           HAVE_LIBIDN2)
1089 _add_if("Largefile"     (CURL_SIZEOF_CURL_OFF_T GREATER 4) AND
1090                         ((SIZEOF_OFF_T GREATER 4) OR USE_WIN32_LARGE_FILES))
1091 # TODO SSP1 (WinSSL) check is missing
1092 _add_if("SSPI"          USE_WINDOWS_SSPI)
1093 _add_if("GSS-API"       HAVE_GSSAPI)
1094 # TODO SSP1 missing for SPNEGO
1095 _add_if("SPNEGO"        NOT CURL_DISABLE_CRYPTO_AUTH AND
1096                         (HAVE_GSSAPI OR USE_WINDOWS_SSPI))
1097 _add_if("Kerberos"      NOT CURL_DISABLE_CRYPTO_AUTH AND
1098                         (HAVE_GSSAPI OR USE_WINDOWS_SSPI))
1099 # NTLM support requires crypto function adaptions from various SSL libs
1100 # TODO alternative SSL libs tests for SSP1, GNUTLS, NSS, DARWINSSL
1101 if(NOT CURL_DISABLE_CRYPTO_AUTH AND (USE_OPENSSL OR
1102    USE_WINDOWS_SSPI OR GNUTLS_ENABLED OR NSS_ENABLED OR DARWINSSL_ENABLED))
1103   _add_if("NTLM"        1)
1104   # TODO missing option (autoconf: --enable-ntlm-wb)
1105   _add_if("NTLM_WB"     NOT CURL_DISABLE_HTTP AND NTLM_WB_ENABLED)
1106 endif()
1107 # TODO missing option (--enable-tls-srp), depends on GNUTLS_SRP/OPENSSL_SRP
1108 _add_if("TLS-SRP"       USE_TLS_SRP)
1109 # TODO option --with-nghttp2 tests for nghttp2 lib and nghttp2/nghttp2.h header
1110 _add_if("HTTP2"         USE_NGHTTP2)
1111 string(REPLACE ";" " " SUPPORT_FEATURES "${_items}")
1112 message(STATUS "Enabled features: ${SUPPORT_FEATURES}")
1113
1114 # Clear list and try to detect available protocols
1115 set(_items)
1116 _add_if("HTTP"          NOT CURL_DISABLE_HTTP)
1117 _add_if("HTTPS"         NOT CURL_DISABLE_HTTP AND SSL_ENABLED)
1118 _add_if("FTP"           NOT CURL_DISABLE_FTP)
1119 _add_if("FTPS"          NOT CURL_DISABLE_FTP AND SSL_ENABLED)
1120 _add_if("FILE"          NOT CURL_DISABLE_FILE)
1121 _add_if("TELNET"        NOT CURL_DISABLE_TELNET)
1122 _add_if("LDAP"          NOT CURL_DISABLE_LDAP)
1123 # CURL_DISABLE_LDAP implies CURL_DISABLE_LDAPS
1124 # TODO check HAVE_LDAP_SSL (in autoconf this is enabled with --enable-ldaps)
1125 _add_if("LDAPS"         NOT CURL_DISABLE_LDAPS AND
1126                         ((USE_OPENLDAP AND SSL_ENABLED) OR
1127                         (NOT USE_OPENLDAP AND HAVE_LDAP_SSL)))
1128 _add_if("DICT"          NOT CURL_DISABLE_DICT)
1129 _add_if("TFTP"          NOT CURL_DISABLE_TFTP)
1130 _add_if("GOPHER"        NOT CURL_DISABLE_GOPHER)
1131 _add_if("POP3"          NOT CURL_DISABLE_POP3)
1132 _add_if("POP3S"         NOT CURL_DISABLE_POP3 AND SSL_ENABLED)
1133 _add_if("IMAP"          NOT CURL_DISABLE_IMAP)
1134 _add_if("IMAPS"         NOT CURL_DISABLE_IMAP AND SSL_ENABLED)
1135 _add_if("SMTP"          NOT CURL_DISABLE_SMTP)
1136 _add_if("SMTPS"         NOT CURL_DISABLE_SMTP AND SSL_ENABLED)
1137 _add_if("SCP"           USE_LIBSSH2)
1138 _add_if("SFTP"          USE_LIBSSH2)
1139 _add_if("RTSP"          NOT CURL_DISABLE_RTSP)
1140 _add_if("RTMP"          USE_LIBRTMP)
1141 list(SORT _items)
1142 string(REPLACE ";" " " SUPPORT_PROTOCOLS "${_items}")
1143 message(STATUS "Enabled protocols: ${SUPPORT_PROTOCOLS}")
1144
1145 # curl-config needs the following options to be set.
1146 set(CC                      "${CMAKE_C_COMPILER}")
1147 # TODO probably put a -D... options here?
1148 set(CONFIGURE_OPTIONS       "")
1149 # TODO when to set "-DCURL_STATICLIB" for CPPFLAG_CURL_STATICLIB?
1150 set(CPPFLAG_CURL_STATICLIB  "")
1151 # TODO need to set this (see CURL_CHECK_CA_BUNDLE in acinclude.m4)
1152 set(CURL_CA_BUNDLE          "")
1153 set(CURLVERSION             "${CURL_VERSION}")
1154 set(ENABLE_SHARED           "yes")
1155 if(CURL_STATICLIB)
1156   set(ENABLE_STATIC         "yes")
1157 else()
1158   set(ENABLE_STATIC         "no")
1159 endif()
1160 set(exec_prefix             "\${prefix}")
1161 set(includedir              "\${prefix}/include")
1162 set(LDFLAGS                 "${CMAKE_SHARED_LINKER_FLAGS}")
1163 set(LIBCURL_LIBS            "")
1164 set(libdir                  "${CMAKE_INSTALL_PREFIX}/lib")
1165 foreach(_lib ${CMAKE_C_IMPLICIT_LINK_LIBRARIES} ${CURL_LIBS})
1166   if(_lib MATCHES ".*/.*")
1167     set(LIBCURL_LIBS          "${LIBCURL_LIBS} ${_lib}")
1168   else()
1169     set(LIBCURL_LIBS          "${LIBCURL_LIBS} -l${_lib}")
1170   endif()
1171 endforeach()
1172 # "a" (Linux) or "lib" (Windows)
1173 string(REPLACE "." "" libext "${CMAKE_STATIC_LIBRARY_SUFFIX}")
1174 set(prefix                  "${CMAKE_INSTALL_PREFIX}")
1175 # Set this to "yes" to append all libraries on which -lcurl is dependent
1176 set(REQUIRE_LIB_DEPS        "no")
1177 # SUPPORT_FEATURES
1178 # SUPPORT_PROTOCOLS
1179 set(VERSIONNUM              "${CURL_VERSION_NUM}")
1180
1181 # Finally generate a "curl-config" matching this config
1182 configure_file("${CURL_SOURCE_DIR}/curl-config.in"
1183                "${CURL_BINARY_DIR}/curl-config" @ONLY)
1184 install(FILES "${CURL_BINARY_DIR}/curl-config"
1185         DESTINATION bin
1186         PERMISSIONS
1187           OWNER_READ OWNER_WRITE OWNER_EXECUTE
1188           GROUP_READ GROUP_EXECUTE
1189           WORLD_READ WORLD_EXECUTE)
1190
1191 # Finally generate a pkg-config file matching this config
1192 configure_file("${CURL_SOURCE_DIR}/libcurl.pc.in"
1193                "${CURL_BINARY_DIR}/libcurl.pc" @ONLY)
1194 install(FILES "${CURL_BINARY_DIR}/libcurl.pc"
1195         DESTINATION lib/pkgconfig)
1196
1197 # This needs to be run very last so other parts of the scripts can take advantage of this.
1198 if(NOT CURL_CONFIG_HAS_BEEN_RUN_BEFORE)
1199   set(CURL_CONFIG_HAS_BEEN_RUN_BEFORE 1 CACHE INTERNAL "Flag to track whether this is the first time running CMake or if CMake has been configured before")
1200 endif()
1201
1202 # Installation.
1203 # First, install generated curlbuild.h
1204 install(FILES "${CMAKE_CURRENT_BINARY_DIR}/include/curl/curlbuild.h"
1205     DESTINATION include/curl )
1206 # Next, install other headers excluding curlbuild.h
1207 install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/include/curl"
1208     DESTINATION include
1209     FILES_MATCHING PATTERN "*.h"
1210     PATTERN "curlbuild.h" EXCLUDE)
1211
1212
1213 # Workaround for MSVS10 to avoid the Dialog Hell
1214 # FIXME: This could be removed with future version of CMake.
1215 if(MSVC_VERSION EQUAL 1600)
1216   set(CURL_SLN_FILENAME "${CMAKE_CURRENT_BINARY_DIR}/CURL.sln")
1217   if(EXISTS "${CURL_SLN_FILENAME}")
1218     file(APPEND "${CURL_SLN_FILENAME}" "\n# This should be regenerated!\n")
1219   endif()
1220 endif()