0421c1c34c6f0107e8f20388db2fc19859023f4f
[platform/upstream/cmake.git] / Utilities / cmcurl / CMake / OtherTests.cmake
1 #***************************************************************************
2 #                                  _   _ ____  _
3 #  Project                     ___| | | |  _ \| |
4 #                             / __| | | | |_) | |
5 #                            | (__| |_| |  _ <| |___
6 #                             \___|\___/|_| \_\_____|
7 #
8 # Copyright (C) 1998 - 2022, 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.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 include(CheckCSourceCompiles)
23 # The begin of the sources (macros and includes)
24 set(_source_epilogue "#undef inline")
25
26 macro(add_header_include check header)
27   if(${check})
28     set(_source_epilogue "${_source_epilogue}\n#include <${header}>")
29   endif()
30 endmacro()
31
32 set(signature_call_conv)
33 if(HAVE_WINDOWS_H)
34   add_header_include(HAVE_WINSOCK2_H "winsock2.h")
35   add_header_include(HAVE_WINDOWS_H "windows.h")
36   set(_source_epilogue
37       "${_source_epilogue}\n#ifndef WIN32_LEAN_AND_MEAN\n#define WIN32_LEAN_AND_MEAN\n#endif")
38   set(signature_call_conv "PASCAL")
39   if(HAVE_LIBWS2_32)
40     set(CMAKE_REQUIRED_LIBRARIES ws2_32)
41   endif()
42 else()
43   add_header_include(HAVE_SYS_TYPES_H "sys/types.h")
44   add_header_include(HAVE_SYS_SOCKET_H "sys/socket.h")
45 endif()
46
47 set(CMAKE_TRY_COMPILE_TARGET_TYPE STATIC_LIBRARY)
48
49 if(1) # CMake hard-codes these
50   set(RECV_TYPE_ARG1 "curl_socket_t")
51   set(RECV_TYPE_ARG2 "char *")
52   set(RECV_TYPE_ARG3 "size_t")
53   set(RECV_TYPE_ARG4 "int")
54   set(RECV_TYPE_RETV "ssize_t")
55 else()
56 function(curl_cv_func_recv_run_test recv_retv recv_arg1 recv_arg2 recv_arg3 recv_arg4)
57   unset(curl_cv_func_recv_test CACHE)
58   check_c_source_compiles("
59     ${_source_epilogue}
60     #ifdef WINSOCK_API_LINKAGE
61     WINSOCK_API_LINKAGE
62     #endif
63     extern ${recv_retv} ${signature_call_conv}
64     recv(${recv_arg1}, ${recv_arg2}, ${recv_arg3}, ${recv_arg4});
65     int main(void) {
66       ${recv_arg1} s=0;
67       ${recv_arg2} buf=0;
68       ${recv_arg3} len=0;
69       ${recv_arg4} flags=0;
70       ${recv_retv} res = recv(s, buf, len, flags);
71       (void) res;
72       return 0;
73     }"
74     curl_cv_func_recv_test)
75   message(STATUS
76     "Tested: ${recv_retv} recv(${recv_arg1}, ${recv_arg2}, ${recv_arg3}, ${recv_arg4})")
77   if(curl_cv_func_recv_test)
78     set(curl_cv_func_recv_args
79       "${recv_arg1},${recv_arg2},${recv_arg3},${recv_arg4},${recv_retv}" PARENT_SCOPE)
80     set(RECV_TYPE_ARG1 "${recv_arg1}" PARENT_SCOPE)
81     set(RECV_TYPE_ARG2 "${recv_arg2}" PARENT_SCOPE)
82     set(RECV_TYPE_ARG3 "${recv_arg3}" PARENT_SCOPE)
83     set(RECV_TYPE_ARG4 "${recv_arg4}" PARENT_SCOPE)
84     set(RECV_TYPE_RETV "${recv_retv}" PARENT_SCOPE)
85     set(HAVE_RECV 1 PARENT_SCOPE)
86     set(curl_cv_func_recv_done 1 PARENT_SCOPE)
87   endif()
88 endfunction()
89
90 check_c_source_compiles("${_source_epilogue}
91 int main(void) {
92     recv(0, 0, 0, 0);
93     return 0;
94 }" curl_cv_recv)
95 if(curl_cv_recv)
96   if(NOT DEFINED curl_cv_func_recv_args OR curl_cv_func_recv_args STREQUAL "unknown")
97     if(APPLE)
98       curl_cv_func_recv_run_test("ssize_t" "int" "void *" "size_t" "int")
99     endif()
100     foreach(recv_retv "int" "ssize_t" )
101       foreach(recv_arg1 "SOCKET" "int" )
102         foreach(recv_arg2 "char *" "void *" )
103           foreach(recv_arg3 "int" "size_t" "socklen_t" "unsigned int")
104             foreach(recv_arg4 "int" "unsigned int")
105               if(NOT curl_cv_func_recv_done)
106                 curl_cv_func_recv_run_test(${recv_retv} ${recv_arg1} ${recv_arg2} ${recv_arg3} ${recv_arg4})
107               endif()
108             endforeach()
109           endforeach()
110         endforeach()
111       endforeach()
112     endforeach()
113   else()
114     string(REGEX REPLACE "^([^,]*),[^,]*,[^,]*,[^,]*,[^,]*$" "\\1" RECV_TYPE_ARG1 "${curl_cv_func_recv_args}")
115     string(REGEX REPLACE "^[^,]*,([^,]*),[^,]*,[^,]*,[^,]*$" "\\1" RECV_TYPE_ARG2 "${curl_cv_func_recv_args}")
116     string(REGEX REPLACE "^[^,]*,[^,]*,([^,]*),[^,]*,[^,]*$" "\\1" RECV_TYPE_ARG3 "${curl_cv_func_recv_args}")
117     string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,([^,]*),[^,]*$" "\\1" RECV_TYPE_ARG4 "${curl_cv_func_recv_args}")
118     string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,[^,]*,([^,]*)$" "\\1" RECV_TYPE_RETV "${curl_cv_func_recv_args}")
119   endif()
120
121   if(curl_cv_func_recv_args STREQUAL "unknown")
122     message(FATAL_ERROR "Cannot find proper types to use for recv args")
123   endif()
124 else()
125   message(FATAL_ERROR "Unable to link function recv")
126 endif()
127 set(curl_cv_func_recv_args "${curl_cv_func_recv_args}" CACHE INTERNAL "Arguments for recv")
128 endif()
129 set(HAVE_RECV 1)
130
131 if(1) # CMake hard-codes these
132   set(SEND_QUAL_ARG2 " ")
133   set(SEND_TYPE_ARG1 "curl_socket_t")
134   set(SEND_TYPE_ARG2 "char *")
135   set(SEND_TYPE_ARG3 "size_t")
136   set(SEND_TYPE_ARG4 "int")
137   set(SEND_TYPE_RETV "ssize_t")
138 else()
139 function(curl_cv_func_send_run_test send_retv send_arg1 send_arg2 send_arg3 send_arg4)
140   unset(curl_cv_func_send_test CACHE)
141   check_c_source_compiles("
142     ${_source_epilogue}
143     #ifdef WINSOCK_API_LINKAGE
144     WINSOCK_API_LINKAGE
145     #endif
146     extern ${send_retv} ${signature_call_conv}
147     send(${send_arg1}, ${send_arg2}, ${send_arg3}, ${send_arg4});
148     int main(void) {
149       ${send_arg1} s=0;
150       ${send_arg2} buf=0;
151       ${send_arg3} len=0;
152       ${send_arg4} flags=0;
153       ${send_retv} res = send(s, buf, len, flags);
154       (void) res;
155       return 0;
156     }"
157     curl_cv_func_send_test)
158   message(STATUS
159     "Tested: ${send_retv} send(${send_arg1}, ${send_arg2}, ${send_arg3}, ${send_arg4})")
160   if(curl_cv_func_send_test)
161     string(REGEX REPLACE "(const) .*" "\\1" send_qual_arg2 "${send_arg2}")
162     string(REGEX REPLACE "const (.*)" "\\1" send_arg2 "${send_arg2}")
163     set(curl_cv_func_send_args
164       "${send_arg1},${send_arg2},${send_arg3},${send_arg4},${send_retv},${send_qual_arg2}" PARENT_SCOPE)
165     set(SEND_TYPE_ARG1 "${send_arg1}" PARENT_SCOPE)
166     set(SEND_TYPE_ARG2 "${send_arg2}" PARENT_SCOPE)
167     set(SEND_TYPE_ARG3 "${send_arg3}" PARENT_SCOPE)
168     set(SEND_TYPE_ARG4 "${send_arg4}" PARENT_SCOPE)
169     set(SEND_TYPE_RETV "${send_retv}" PARENT_SCOPE)
170     set(HAVE_SEND 1 PARENT_SCOPE)
171     set(curl_cv_func_send_done 1 PARENT_SCOPE)
172   endif()
173 endfunction()
174
175 check_c_source_compiles("${_source_epilogue}
176 int main(void) {
177     send(0, 0, 0, 0);
178     return 0;
179 }" curl_cv_send)
180 if(curl_cv_send)
181   if(NOT DEFINED curl_cv_func_send_args OR "${curl_cv_func_send_args}" STREQUAL "unknown")
182     if(APPLE)
183       curl_cv_func_send_run_test("ssize_t" "int" "const void *" "size_t" "int")
184     endif()
185     foreach(send_retv "int" "ssize_t" )
186       foreach(send_arg1 "SOCKET" "int" "ssize_t" )
187         foreach(send_arg2 "const char *" "const void *" "void *" "char *")
188           foreach(send_arg3 "int" "size_t" "socklen_t" "unsigned int")
189             foreach(send_arg4 "int" "unsigned int")
190               if(NOT curl_cv_func_send_done)
191                 curl_cv_func_send_run_test("${send_retv}" "${send_arg1}" "${send_arg2}" "${send_arg3}" "${send_arg4}")
192               endif()
193             endforeach()
194           endforeach()
195         endforeach()
196       endforeach()
197     endforeach()
198   else()
199     string(REGEX REPLACE "^([^,]*),[^,]*,[^,]*,[^,]*,[^,]*,[^,]*$" "\\1" SEND_TYPE_ARG1 "${curl_cv_func_send_args}")
200     string(REGEX REPLACE "^[^,]*,([^,]*),[^,]*,[^,]*,[^,]*,[^,]*$" "\\1" SEND_TYPE_ARG2 "${curl_cv_func_send_args}")
201     string(REGEX REPLACE "^[^,]*,[^,]*,([^,]*),[^,]*,[^,]*,[^,]*$" "\\1" SEND_TYPE_ARG3 "${curl_cv_func_send_args}")
202     string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,([^,]*),[^,]*,[^,]*$" "\\1" SEND_TYPE_ARG4 "${curl_cv_func_send_args}")
203     string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,[^,]*,([^,]*),[^,]*$" "\\1" SEND_TYPE_RETV "${curl_cv_func_send_args}")
204     string(REGEX REPLACE "^[^,]*,[^,]*,[^,]*,[^,]*,[^,]*,([^,]*)$" "\\1" SEND_QUAL_ARG2 "${curl_cv_func_send_args}")
205   endif()
206
207   if("${curl_cv_func_send_args}" STREQUAL "unknown")
208     message(FATAL_ERROR "Cannot find proper types to use for send args")
209   endif()
210   set(SEND_QUAL_ARG2 "const")
211 else()
212   message(FATAL_ERROR "Unable to link function send")
213 endif()
214 set(curl_cv_func_send_args "${curl_cv_func_send_args}" CACHE INTERNAL "Arguments for send")
215 endif()
216 set(HAVE_SEND 1)
217
218 check_c_source_compiles("${_source_epilogue}
219   int main(void) {
220     int flag = MSG_NOSIGNAL;
221     (void)flag;
222     return 0;
223   }" HAVE_MSG_NOSIGNAL)
224
225 if(NOT HAVE_WINDOWS_H)
226   add_header_include(HAVE_SYS_TIME_H "sys/time.h")
227   add_header_include(TIME_WITH_SYS_TIME "time.h")
228   add_header_include(HAVE_TIME_H "time.h")
229 endif()
230 check_c_source_compiles("${_source_epilogue}
231 int main(void) {
232   struct timeval ts;
233   ts.tv_sec  = 0;
234   ts.tv_usec = 0;
235   (void)ts;
236   return 0;
237 }" HAVE_STRUCT_TIMEVAL)
238
239 if(HAVE_WINDOWS_H)
240   set(CMAKE_EXTRA_INCLUDE_FILES winsock2.h)
241 else()
242   set(CMAKE_EXTRA_INCLUDE_FILES)
243   if(HAVE_SYS_SOCKET_H)
244     set(CMAKE_EXTRA_INCLUDE_FILES sys/socket.h)
245   endif()
246 endif()
247
248 check_type_size("struct sockaddr_storage" SIZEOF_STRUCT_SOCKADDR_STORAGE)
249 if(HAVE_SIZEOF_STRUCT_SOCKADDR_STORAGE)
250   set(HAVE_STRUCT_SOCKADDR_STORAGE 1)
251 endif()
252
253 unset(CMAKE_TRY_COMPILE_TARGET_TYPE)
254
255 if(NOT DEFINED CMAKE_TOOLCHAIN_FILE)
256   if(NOT ${CMAKE_SYSTEM_NAME} MATCHES "Darwin" AND NOT ${CMAKE_SYSTEM_NAME} MATCHES "iOS")
257   # only try this on non-apple platforms
258
259   # if not cross-compilation...
260   include(CheckCSourceRuns)
261   set(CMAKE_REQUIRED_FLAGS "")
262   if(HAVE_SYS_POLL_H)
263     set(CMAKE_REQUIRED_FLAGS "-DHAVE_SYS_POLL_H")
264   elseif(HAVE_POLL_H)
265     set(CMAKE_REQUIRED_FLAGS "-DHAVE_POLL_H")
266   endif()
267   check_c_source_runs("
268     #include <stdlib.h>
269     #include <sys/time.h>
270
271     #ifdef HAVE_SYS_POLL_H
272     #  include <sys/poll.h>
273     #elif  HAVE_POLL_H
274     #  include <poll.h>
275     #endif
276
277     int main(void)
278     {
279         if(0 != poll(0, 0, 10)) {
280           return 1; /* fail */
281         }
282         else {
283           /* detect the 10.12 poll() breakage */
284           struct timeval before, after;
285           int rc;
286           size_t us;
287
288           gettimeofday(&before, NULL);
289           rc = poll(NULL, 0, 500);
290           gettimeofday(&after, NULL);
291
292           us = (after.tv_sec - before.tv_sec) * 1000000 +
293             (after.tv_usec - before.tv_usec);
294
295           if(us < 400000) {
296             return 1;
297           }
298         }
299         return 0;
300     }" HAVE_POLL_FINE)
301   endif()
302 endif()
303