Mercurial > octave
comparison m4/prog_c.m4 @ 21304:0cf6c08cb252
configure.ac: check support for C11 and C++11 (patch #8906)
* configure.ac: two new checks for support of C++11 and C11 versions of
the standard and to add required flags to CXX and CC. These need to
be done before AC_PROG_CPP and AC_PROG_CXXPP since the later will
make use of the defined CXX and CC.
* m4/prog_c.m4, m4/prog_cxx.m4: added files for OCTAVE_PROG_CC_C11 and
OCTAVE_PROG_CXX_CXX11 which are copied from autoconf source tree
implementations of _AC_PROG_CC_C11 and _AC_PROG_CXX_CXX11.
author | Carnë Draug <carandraug@octave.org> |
---|---|
date | Thu, 18 Feb 2016 16:20:49 +0000 |
parents | |
children | 822dc5a202c9 |
comparison
equal
deleted
inserted
replaced
21303:325e04c63f8c | 21304:0cf6c08cb252 |
---|---|
1 # Copyright (C) 2001-2016 Free Software Foundation, Inc. | |
2 # | |
3 # | |
4 # This is pretty much copy and paste of the unreleased autoconf macros | |
5 # (where it is named AC_PROG_CXX_CXX11). Once we are dependent on | |
6 # autoconf version with that macro, we can simply change to use that | |
7 # one instead. Copied from autoconf commit 04be2b7a (2016/02/06) | |
8 # | |
9 # | |
10 # This file is part of Autoconf. This program is free | |
11 # software; you can redistribute it and/or modify it under the | |
12 # terms of the GNU General Public License as published by the | |
13 # Free Software Foundation, either version 3 of the License, or | |
14 # (at your option) any later version. | |
15 # | |
16 # This program is distributed in the hope that it will be useful, | |
17 # but WITHOUT ANY WARRANTY; without even the implied warranty of | |
18 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
19 # GNU General Public License for more details. | |
20 # | |
21 # You should have received a copy of the GNU General Public License | |
22 # along with this program; if not, see <http://www.gnu.org/licenses/>. | |
23 | |
24 # OCTAVE_PROG_CC_C11 ([ACTION-IF-AVAILABLE], [ACTION-IF-UNAVAILABLE]) | |
25 # ---------------------------------------------------------------- | |
26 # If the C compiler is not in ISO C11 mode by default, try to add an | |
27 # option to output variable CC to make it so. This macro tries | |
28 # various options that select ISO C11 on some system or another. It | |
29 # considers the compiler to be in ISO C11 mode if it handles _Alignas, | |
30 # _Alignof, _Noreturn, _Static_assert, UTF-8 string literals, | |
31 # duplicate typedefs, and anonymous structures and unions. | |
32 AC_DEFUN([OCTAVE_PROG_CC_C11], | |
33 [_OCTAVE_C_STD_TRY([c11], | |
34 [_OCTAVE_C_C99_TEST_HEADER[ | |
35 // Check _Alignas. | |
36 char _Alignas (double) aligned_as_double; | |
37 char _Alignas (0) no_special_alignment; | |
38 extern char aligned_as_int; | |
39 char _Alignas (0) _Alignas (int) aligned_as_int; | |
40 | |
41 // Check _Alignof. | |
42 enum | |
43 { | |
44 int_alignment = _Alignof (int), | |
45 int_array_alignment = _Alignof (int[100]), | |
46 char_alignment = _Alignof (char) | |
47 }; | |
48 _Static_assert (0 < -_Alignof (int), "_Alignof is signed"); | |
49 | |
50 // Check _Noreturn. | |
51 int _Noreturn does_not_return (void) { for (;;) continue; } | |
52 | |
53 // Check _Static_assert. | |
54 struct test_static_assert | |
55 { | |
56 int x; | |
57 _Static_assert (sizeof (int) <= sizeof (long int), | |
58 "_Static_assert does not work in struct"); | |
59 long int y; | |
60 }; | |
61 | |
62 // Check UTF-8 literals. | |
63 #define u8 syntax error! | |
64 char const utf8_literal[] = u8"happens to be ASCII" "another string"; | |
65 | |
66 // Check duplicate typedefs. | |
67 typedef long *long_ptr; | |
68 typedef long int *long_ptr; | |
69 typedef long_ptr long_ptr; | |
70 | |
71 // Anonymous structures and unions -- taken from C11 6.7.2.1 Example 1. | |
72 struct anonymous | |
73 { | |
74 union { | |
75 struct { int i; int j; }; | |
76 struct { int k; long int l; } w; | |
77 }; | |
78 int m; | |
79 } v1; | |
80 ]], | |
81 [_OCTAVE_C_C99_TEST_BODY[ | |
82 v1.i = 2; | |
83 v1.w.k = 5; | |
84 _Static_assert (&v1.i == &v1.w.k, "Anonymous union alignment botch"); | |
85 ]], | |
86 dnl Try | |
87 dnl GCC -std=gnu11 (unused restrictive mode: -std=c11) | |
88 dnl with extended modes being tried first. | |
89 dnl | |
90 dnl Do not try -qlanglvl=extc1x, because IBM XL C V12.1 (the latest version as | |
91 dnl of September 2012) does not pass the C11 test. For now, try extc1x when | |
92 dnl compiling the C99 test instead, since it enables _Static_assert and | |
93 dnl _Noreturn, which is a win. If -qlanglvl=extc11 or -qlanglvl=extc1x passes | |
94 dnl the C11 test in some future version of IBM XL C, we'll add it here, | |
95 dnl preferably extc11. | |
96 [[-std=gnu11]], [$1], [$2])[]dnl | |
97 ])# OCTAVE_PROG_CC_C11 | |
98 | |
99 | |
100 # _OCTAVE_C_STD_TRY(STANDARD, TEST-PROLOGUE, TEST-BODY, OPTION-LIST, | |
101 # ACTION-IF-AVAILABLE, ACTION-IF-UNAVAILABLE) | |
102 # -------------------------------------------------------------- | |
103 # Check whether the C compiler accepts features of STANDARD (e.g `c89', `c99') | |
104 # by trying to compile a program of TEST-PROLOGUE and TEST-BODY. If this fails, | |
105 # try again with each compiler option in the space-separated OPTION-LIST; if one | |
106 # helps, append it to CC. If eventually successful, run ACTION-IF-AVAILABLE, | |
107 # else ACTION-IF-UNAVAILABLE. | |
108 AC_DEFUN([_OCTAVE_C_STD_TRY], | |
109 [AC_MSG_CHECKING([for $CC option to enable ]m4_translit($1, [c], [C])[ features]) | |
110 AC_CACHE_VAL(ac_cv_prog_cc_$1, | |
111 [ac_cv_prog_cc_$1=no | |
112 ac_save_CC=$CC | |
113 AC_LANG_CONFTEST([AC_LANG_PROGRAM([$2], [$3])]) | |
114 for ac_arg in '' $4 | |
115 do | |
116 CC="$ac_save_CC $ac_arg" | |
117 _AC_COMPILE_IFELSE([], [ac_cv_prog_cc_$1=$ac_arg]) | |
118 test "x$ac_cv_prog_cc_$1" != "xno" && break | |
119 done | |
120 rm -f conftest.$ac_ext | |
121 CC=$ac_save_CC | |
122 ])# AC_CACHE_VAL | |
123 ac_prog_cc_stdc_options= | |
124 case "x$ac_cv_prog_cc_$1" in | |
125 x) | |
126 AC_MSG_RESULT([none needed]) ;; | |
127 xno) | |
128 AC_MSG_RESULT([unsupported]) ;; | |
129 *) | |
130 ac_prog_cc_stdc_options=" $ac_cv_prog_cc_$1" | |
131 CC=$CC$ac_prog_cc_stdc_options | |
132 AC_MSG_RESULT([$ac_cv_prog_cc_$1]) ;; | |
133 esac | |
134 AS_IF([test "x$ac_cv_prog_cc_$1" != xno], [$5], [$6]) | |
135 ])# _OCTAVE_C_STD_TRY | |
136 | |
137 # _OCTAVE_C_C99_TEST_HEADER | |
138 # --------------------- | |
139 # A C header suitable for testing for C99. | |
140 AC_DEFUN([_OCTAVE_C_C99_TEST_HEADER], | |
141 [[#include <stdarg.h> | |
142 #include <stdbool.h> | |
143 #include <stdlib.h> | |
144 #include <wchar.h> | |
145 #include <stdio.h> | |
146 | |
147 // Check varargs macros. These examples are taken from C99 6.10.3.5. | |
148 #define debug(...) fprintf (stderr, __VA_ARGS__) | |
149 #define showlist(...) puts (#__VA_ARGS__) | |
150 #define report(test,...) ((test) ? puts (#test) : printf (__VA_ARGS__)) | |
151 static void | |
152 test_varargs_macros (void) | |
153 { | |
154 int x = 1234; | |
155 int y = 5678; | |
156 debug ("Flag"); | |
157 debug ("X = %d\n", x); | |
158 showlist (The first, second, and third items.); | |
159 report (x>y, "x is %d but y is %d", x, y); | |
160 } | |
161 | |
162 // Check long long types. | |
163 #define BIG64 18446744073709551615ull | |
164 #define BIG32 4294967295ul | |
165 #define BIG_OK (BIG64 / BIG32 == 4294967297ull && BIG64 % BIG32 == 0) | |
166 #if !BIG_OK | |
167 your preprocessor is broken; | |
168 #endif | |
169 #if BIG_OK | |
170 #else | |
171 your preprocessor is broken; | |
172 #endif | |
173 static long long int bignum = -9223372036854775807LL; | |
174 static unsigned long long int ubignum = BIG64; | |
175 | |
176 struct incomplete_array | |
177 { | |
178 int datasize; | |
179 double data[]; | |
180 }; | |
181 | |
182 struct named_init { | |
183 int number; | |
184 const wchar_t *name; | |
185 double average; | |
186 }; | |
187 | |
188 typedef const char *ccp; | |
189 | |
190 static inline int | |
191 test_restrict (ccp restrict text) | |
192 { | |
193 // See if C++-style comments work. | |
194 // Iterate through items via the restricted pointer. | |
195 // Also check for declarations in for loops. | |
196 for (unsigned int i = 0; *(text+i) != '\0'; ++i) | |
197 continue; | |
198 return 0; | |
199 } | |
200 | |
201 // Check varargs and va_copy. | |
202 static bool | |
203 test_varargs (const char *format, ...) | |
204 { | |
205 va_list args; | |
206 va_start (args, format); | |
207 va_list args_copy; | |
208 va_copy (args_copy, args); | |
209 | |
210 const char *str = ""; | |
211 int number = 0; | |
212 float fnumber = 0; | |
213 | |
214 while (*format) | |
215 { | |
216 switch (*format++) | |
217 { | |
218 case 's': // string | |
219 str = va_arg (args_copy, const char *); | |
220 break; | |
221 case 'd': // int | |
222 number = va_arg (args_copy, int); | |
223 break; | |
224 case 'f': // float | |
225 fnumber = va_arg (args_copy, double); | |
226 break; | |
227 default: | |
228 break; | |
229 } | |
230 } | |
231 va_end (args_copy); | |
232 va_end (args); | |
233 | |
234 return *str && number && fnumber; | |
235 }]])# _OCTAVE_C_C99_TEST_HEADER | |
236 | |
237 # _OCTAVE_C_C99_TEST_BODY | |
238 # ------------------- | |
239 # A C body suitable for testing for C99, assuming the corresponding header. | |
240 AC_DEFUN([_OCTAVE_C_C99_TEST_BODY], | |
241 [[ | |
242 // Check bool. | |
243 _Bool success = false; | |
244 | |
245 // Check restrict. | |
246 if (test_restrict ("String literal") == 0) | |
247 success = true; | |
248 char *restrict newvar = "Another string"; | |
249 | |
250 // Check varargs. | |
251 success &= test_varargs ("s, d' f .", "string", 65, 34.234); | |
252 test_varargs_macros (); | |
253 | |
254 // Check flexible array members. | |
255 struct incomplete_array *ia = | |
256 malloc (sizeof (struct incomplete_array) + (sizeof (double) * 10)); | |
257 ia->datasize = 10; | |
258 for (int i = 0; i < ia->datasize; ++i) | |
259 ia->data[i] = i * 1.234; | |
260 | |
261 // Check named initializers. | |
262 struct named_init ni = { | |
263 .number = 34, | |
264 .name = L"Test wide string", | |
265 .average = 543.34343, | |
266 }; | |
267 | |
268 ni.number = 58; | |
269 | |
270 int dynamic_array[ni.number]; | |
271 dynamic_array[ni.number - 1] = 543; | |
272 | |
273 // work around unused variable warnings | |
274 return (!success || bignum == 0LL || ubignum == 0uLL || newvar[0] == 'x' | |
275 || dynamic_array[ni.number - 1] != 543); | |
276 ]]) |