1 # a waf tool to add autoconf-like macros to the configure section
3 import Build
, os
, sys
, Options
, preproc
, Logs
5 from Configure
import conf
6 from samba_utils
import *
9 missing_headers
= set()
11 ####################################################
12 # some autoconf like helpers, to make the transition
13 # to waf a bit easier for those used to autoconf
18 def DEFINE(conf
, d
, v
, add_to_cflags
=False, quote
=False):
19 '''define a config option'''
20 conf
.define(d
, v
, quote
=quote
)
22 conf
.env
.append_value('CCDEFINES', d
+ '=' + str(v
))
24 def hlist_to_string(conf
, headers
=None):
25 '''convert a headers list to a set of #include lines'''
27 hlist
= conf
.env
.hlist
30 hlist
.extend(TO_LIST(headers
))
32 hdrs
+= '#include <%s>\n' % h
37 def COMPOUND_START(conf
, msg
):
38 '''start a compound test'''
39 def null_check_message_1(self
,*k
,**kw
):
41 def null_check_message_2(self
,*k
,**kw
):
44 v
= getattr(conf
.env
, 'in_compound', [])
45 if v
!= [] and v
!= 0:
46 conf
.env
.in_compound
= v
+ 1
48 conf
.check_message_1(msg
)
49 conf
.saved_check_message_1
= conf
.check_message_1
50 conf
.check_message_1
= null_check_message_1
51 conf
.saved_check_message_2
= conf
.check_message_2
52 conf
.check_message_2
= null_check_message_2
53 conf
.env
.in_compound
= 1
57 def COMPOUND_END(conf
, result
):
58 '''start a compound test'''
59 conf
.env
.in_compound
-= 1
60 if conf
.env
.in_compound
!= 0:
62 conf
.check_message_1
= conf
.saved_check_message_1
63 conf
.check_message_2
= conf
.saved_check_message_2
64 p
= conf
.check_message_2
68 p('not found', 'YELLOW')
75 '''using the nolink type in conf.check() allows us to avoid
76 the link stage of a test, thus speeding it up for tests
77 that where linking is not needed'''
81 def CHECK_HEADER(conf
, h
, add_headers
=False, lib
=None):
82 '''check for a header'''
83 if h
in missing_headers
and lib
is None:
85 d
= h
.upper().replace('/', '_')
86 d
= d
.replace('.', '_')
87 d
= d
.replace('-', '_')
89 if CONFIG_SET(conf
, d
):
91 if not h
in conf
.env
.hlist
:
92 conf
.env
.hlist
.append(h
)
95 (ccflags
, ldflags
) = library_flags(conf
, lib
)
97 hdrs
= hlist_to_string(conf
, headers
=h
)
98 ret
= conf
.check(fragment
='%s\nint main(void) { return 0; }' % hdrs
,
102 msg
="Checking for header %s" % h
)
104 missing_headers
.add(h
)
108 if add_headers
and not h
in conf
.env
.hlist
:
109 conf
.env
.hlist
.append(h
)
114 def CHECK_HEADERS(conf
, headers
, add_headers
=False, together
=False, lib
=None):
115 '''check for a list of headers
117 when together==True, then the headers accumulate within this test.
118 This is useful for interdependent headers
121 if not add_headers
and together
:
122 saved_hlist
= conf
.env
.hlist
[:]
123 set_add_headers
= True
125 set_add_headers
= add_headers
126 for hdr
in TO_LIST(headers
):
127 if not CHECK_HEADER(conf
, hdr
, set_add_headers
, lib
=lib
):
129 if not add_headers
and together
:
130 conf
.env
.hlist
= saved_hlist
134 def header_list(conf
, headers
=None, lib
=None):
135 '''form a list of headers which exist, as a string'''
137 if headers
is not None:
138 for h
in TO_LIST(headers
):
139 if CHECK_HEADER(conf
, h
, add_headers
=False, lib
=lib
):
141 return hlist_to_string(conf
, headers
=hlist
)
145 def CHECK_TYPE(conf
, t
, alternate
=None, headers
=None, define
=None, lib
=None, msg
=None):
146 '''check for a single type'''
148 define
= 'HAVE_' + t
.upper().replace(' ', '_')
150 msg
='Checking for %s' % t
151 ret
= CHECK_CODE(conf
, '%s _x' % t
,
159 if not ret
and alternate
:
160 conf
.DEFINE(t
, alternate
)
165 def CHECK_TYPES(conf
, list, headers
=None, define
=None, alternate
=None, lib
=None):
166 '''check for a list of types'''
168 for t
in TO_LIST(list):
169 if not CHECK_TYPE(conf
, t
, headers
=headers
,
170 define
=define
, alternate
=alternate
, lib
=lib
):
176 def CHECK_TYPE_IN(conf
, t
, headers
=None, alternate
=None, define
=None):
177 '''check for a single type with a header'''
178 return CHECK_TYPE(conf
, t
, headers
=headers
, alternate
=alternate
, define
=define
)
182 def CHECK_VARIABLE(conf
, v
, define
=None, always
=False,
183 headers
=None, msg
=None, lib
=None):
184 '''check for a variable declaration (or define)'''
186 define
= 'HAVE_%s' % v
.upper()
189 msg
="Checking for variable %s" % v
191 return CHECK_CODE(conf
,
192 # we need to make sure the compiler doesn't
196 void *_x; _x=(void *)&%s; return (int)_x;
211 def CHECK_DECLS(conf
, vars, reverse
=False, headers
=None, always
=False):
212 '''check a list of variable declarations, using the HAVE_DECL_xxx form
215 When reverse==True then use HAVE_xxx_DECL instead of HAVE_DECL_xxx
218 for v
in TO_LIST(vars):
220 define
='HAVE_DECL_%s' % v
.upper()
222 define
='HAVE_%s_DECL' % v
.upper()
223 if not CHECK_VARIABLE(conf
, v
,
226 msg
='Checking for declaration of %s' % v
,
232 def CHECK_FUNC(conf
, f
, link
=True, lib
=None, headers
=None):
233 '''check for a function'''
234 define
='HAVE_%s' % f
.upper()
238 conf
.COMPOUND_START('Checking for %s' % f
)
240 if link
is None or link
== True:
241 ret
= CHECK_CODE(conf
,
242 # this is based on the autoconf strategy
244 #define %s __fake__%s
251 #if defined __stub_%s || defined __stub___%s
252 #error "bad glibc stub"
255 int main() { return %s(); }
256 ''' % (f
, f
, f
, f
, f
, f
, f
),
265 msg
='Checking for %s' % f
)
268 ret
= CHECK_CODE(conf
,
269 # it might be a macro
270 # we need to make sure the compiler doesn't
272 'void *__x = (void *)%s; return (int)__x' % f
,
281 msg
='Checking for macro %s' % f
)
283 if not ret
and (link
is None or link
== False):
284 ret
= CHECK_VARIABLE(conf
, f
,
287 msg
='Checking for declaration of %s' % f
)
288 conf
.COMPOUND_END(ret
)
293 def CHECK_FUNCS(conf
, list, link
=True, lib
=None, headers
=None):
294 '''check for a list of functions'''
296 for f
in TO_LIST(list):
297 if not CHECK_FUNC(conf
, f
, link
=link
, lib
=lib
, headers
=headers
):
303 def CHECK_SIZEOF(conf
, vars, headers
=None, define
=None):
304 '''check the size of a type'''
306 for v
in TO_LIST(vars):
309 v_define
= 'SIZEOF_%s' % v
.upper().replace(' ', '_')
310 if not CHECK_CODE(conf
,
311 'printf("%%u", (unsigned)sizeof(%s))' % v
,
318 msg
="Checking size of %s" % v
):
325 def CHECK_CODE(conf
, code
, define
,
326 always
=False, execute
=False, addmain
=True,
327 add_headers
=True, mandatory
=False,
328 headers
=None, msg
=None, cflags
='', includes
='# .',
329 local_include
=True, lib
=None, link
=True,
330 define_ret
=False, quote
=False,
332 '''check if some code compiles and/or runs'''
334 if CONFIG_SET(conf
, define
):
337 if headers
is not None:
338 CHECK_HEADERS(conf
, headers
=headers
, lib
=lib
)
341 hdrs
= header_list(conf
, headers
=headers
, lib
=lib
)
349 defs
= conf
.get_config_header()
352 fragment
='%s\n%s\n int main(void) { %s; return 0; }\n' % (defs
, hdrs
, code
)
354 fragment
='%s\n%s\n%s\n' % (defs
, hdrs
, code
)
357 msg
="Checking for %s" % define
359 cflags
= TO_LIST(cflags
)
362 cflags
.append('-I%s' % conf
.curdir
)
369 uselib
= TO_LIST(lib
)
371 (ccflags
, ldflags
) = library_flags(conf
, uselib
)
373 cflags
.extend(ccflags
)
376 exec_args
= conf
.SAMBA_CROSS_ARGS(msg
=msg
)
380 conf
.COMPOUND_START(msg
)
382 ret
= conf
.check(fragment
=fragment
,
384 define_name
= define
,
385 mandatory
= mandatory
,
394 define_ret
=define_ret
)
395 if not ret
and CONFIG_SET(conf
, define
):
396 # sometimes conf.check() returns false, but it
397 # sets the define. Maybe a waf bug?
401 conf
.DEFINE(define
, 1)
402 conf
.COMPOUND_END(True)
404 conf
.COMPOUND_END(conf
.env
[define
])
407 conf
.DEFINE(define
, 0)
408 conf
.COMPOUND_END(False)
414 def CHECK_STRUCTURE_MEMBER(conf
, structname
, member
,
415 always
=False, define
=None, headers
=None):
416 '''check for a structure member'''
418 define
= 'HAVE_%s' % member
.upper()
419 return CHECK_CODE(conf
,
420 '%s s; void *_x; _x=(void *)&s.%s' % (structname
, member
),
427 msg
="Checking for member %s in %s" % (member
, structname
))
431 def CHECK_CFLAGS(conf
, cflags
):
432 '''check if the given cflags are accepted by the compiler
434 return conf
.check(fragment
='int main(void) { return 0; }\n',
438 msg
="Checking compiler accepts %s" % cflags
)
441 def CHECK_LDFLAGS(conf
, ldflags
):
442 '''check if the given ldflags are accepted by the linker
444 return conf
.check(fragment
='int main(void) { return 0; }\n',
447 msg
="Checking linker accepts %s" % ldflags
)
451 def CONFIG_GET(conf
, option
):
452 '''return True if a configuration option was found'''
453 if (option
in conf
.env
):
454 return conf
.env
[option
]
459 def CONFIG_SET(conf
, option
):
460 '''return True if a configuration option was found'''
461 return (option
in conf
.env
) and (conf
.env
[option
] != ())
462 Build
.BuildContext
.CONFIG_SET
= CONFIG_SET
463 Build
.BuildContext
.CONFIG_GET
= CONFIG_GET
466 def library_flags(self
, libs
):
467 '''work out flags from pkg_config'''
470 for lib
in TO_LIST(libs
):
471 inc_path
= getattr(self
.env
, 'CPPPATH_%s' % lib
.upper(), [])
472 lib_path
= getattr(self
.env
, 'LIBPATH_%s' % lib
.upper(), [])
473 ccflags
.extend(['-I%s' % i
for i
in inc_path
])
474 ldflags
.extend(['-L%s' % l
for l
in lib_path
])
475 extra_ccflags
= TO_LIST(getattr(self
.env
, 'CCFLAGS_%s' % lib
.upper(), []))
476 extra_ldflags
= TO_LIST(getattr(self
.env
, 'LDFLAGS_%s' % lib
.upper(), []))
477 ccflags
.extend(extra_ccflags
)
478 ldflags
.extend(extra_ldflags
)
479 if 'EXTRA_LDFLAGS' in self
.env
:
480 ldflags
.extend(self
.env
['EXTRA_LDFLAGS'])
482 ccflags
= unique_list(ccflags
)
483 ldflags
= unique_list(ldflags
)
484 return (ccflags
, ldflags
)
488 def CHECK_LIB(conf
, libs
, mandatory
=False, empty_decl
=True, set_target
=True, shlib
=False):
489 '''check if a set of libraries exist as system libraries
491 returns the sublist of libs that do exist as a syslib or []
502 liblist
= TO_LIST(libs
)
503 for lib
in liblist
[:]:
504 if GET_TARGET_TYPE(conf
, lib
) == 'SYSLIB':
508 (ccflags
, ldflags
) = library_flags(conf
, lib
)
510 res
= conf
.check(features
='cc cshlib', fragment
=fragment
, lib
=lib
, uselib_store
=lib
, ccflags
=ccflags
, ldflags
=ldflags
)
512 res
= conf
.check(lib
=lib
, uselib_store
=lib
, ccflags
=ccflags
, ldflags
=ldflags
)
516 Logs
.error("Mandatory library '%s' not found for functions '%s'" % (lib
, list))
519 # if it isn't a mandatory library, then remove it from dependency lists
521 SET_TARGET_TYPE(conf
, lib
, 'EMPTY')
523 conf
.define('HAVE_LIB%s' % lib
.upper().replace('-','_'), 1)
524 conf
.env
['LIB_' + lib
.upper()] = lib
526 conf
.SET_TARGET_TYPE(lib
, 'SYSLIB')
534 def CHECK_FUNCS_IN(conf
, list, library
, mandatory
=False, checklibc
=False,
535 headers
=None, link
=True, empty_decl
=True, set_target
=True):
537 check that the functions in 'list' are available in 'library'
538 if they are, then make that library available as a dependency
540 if the library is not available and mandatory==True, then
543 If the library is not available and mandatory==False, then
544 add the library to the list of dependencies to remove from
547 optionally check for the functions first in libc
549 remaining
= TO_LIST(list)
550 liblist
= TO_LIST(library
)
552 # check if some already found
553 for f
in remaining
[:]:
554 if CONFIG_SET(conf
, 'HAVE_%s' % f
.upper()):
557 # see if the functions are in libc
559 for f
in remaining
[:]:
560 if CHECK_FUNC(conf
, f
, link
=True, headers
=headers
):
565 if GET_TARGET_TYPE(conf
, lib
) != 'SYSLIB' and empty_decl
:
566 SET_TARGET_TYPE(conf
, lib
, 'EMPTY')
569 checklist
= conf
.CHECK_LIB(liblist
, empty_decl
=empty_decl
, set_target
=set_target
)
570 for lib
in liblist
[:]:
571 if not lib
in checklist
and mandatory
:
572 Logs
.error("Mandatory library '%s' not found for functions '%s'" % (lib
, list))
577 if not CHECK_FUNC(conf
, f
, lib
=' '.join(checklist
), headers
=headers
, link
=link
):
584 def IN_LAUNCH_DIR(conf
):
585 '''return True if this rule is being run from the launch directory'''
586 return os
.path
.realpath(conf
.curdir
) == os
.path
.realpath(Options
.launch_dir
)
587 Options
.Handler
.IN_LAUNCH_DIR
= IN_LAUNCH_DIR
591 def SAMBA_CONFIG_H(conf
, path
=None):
592 '''write out config.h in the right directory'''
593 # we don't want to produce a config.h in places like lib/replace
594 # when we are building projects that depend on lib/replace
595 if not IN_LAUNCH_DIR(conf
):
598 if Options
.options
.developer
:
599 # we add these here to ensure that -Wstrict-prototypes is not set during configure
600 conf
.ADD_CFLAGS('-Wall -g -Wshadow -Wstrict-prototypes -Wpointer-arith -Wcast-align -Wwrite-strings -Werror-implicit-function-declaration -Wformat=2 -Wno-format-y2k -Wmissing-prototypes',
602 if os
.getenv('TOPLEVEL_BUILD'):
603 conf
.ADD_CFLAGS('-Wcast-qual', testflags
=True)
604 conf
.env
.DEVELOPER_MODE
= True
606 if Options
.options
.picky_developer
:
607 conf
.ADD_CFLAGS('-Werror', testflags
=True)
609 if Options
.options
.fatal_errors
:
610 conf
.ADD_CFLAGS('-Wfatal-errors', testflags
=True)
612 if Options
.options
.pedantic
:
613 conf
.ADD_CFLAGS('-W', testflags
=True)
616 conf
.write_config_header('config.h', top
=True)
618 conf
.write_config_header(path
)
619 conf
.SAMBA_CROSS_CHECK_COMPLETE()
623 def CONFIG_PATH(conf
, name
, default
):
624 '''setup a configurable path'''
625 if not name
in conf
.env
:
626 if default
[0] == '/':
627 conf
.env
[name
] = default
629 conf
.env
[name
] = conf
.env
['PREFIX'] + default
632 def ADD_CFLAGS(conf
, flags
, testflags
=False):
633 '''add some CFLAGS to the command line
634 optionally set testflags to ensure all the flags work
638 for f
in flags
.split():
639 if CHECK_CFLAGS(conf
, f
):
642 if not 'EXTRA_CFLAGS' in conf
.env
:
643 conf
.env
['EXTRA_CFLAGS'] = []
644 conf
.env
['EXTRA_CFLAGS'].extend(TO_LIST(flags
))
647 def ADD_LDFLAGS(conf
, flags
, testflags
=False):
648 '''add some LDFLAGS to the command line
649 optionally set testflags to ensure all the flags work
651 this will return the flags that are added, if any
655 for f
in flags
.split():
656 if CHECK_LDFLAGS(conf
, f
):
659 if not 'EXTRA_LDFLAGS' in conf
.env
:
660 conf
.env
['EXTRA_LDFLAGS'] = []
661 conf
.env
['EXTRA_LDFLAGS'].extend(TO_LIST(flags
))
666 def ADD_EXTRA_INCLUDES(conf
, includes
):
667 '''add some extra include directories to all builds'''
668 if not 'EXTRA_INCLUDES' in conf
.env
:
669 conf
.env
['EXTRA_INCLUDES'] = []
670 conf
.env
['EXTRA_INCLUDES'].extend(TO_LIST(includes
))
674 def CURRENT_CFLAGS(bld
, target
, cflags
, hide_symbols
=False):
675 '''work out the current flags. local flags are added first'''
676 if not 'EXTRA_CFLAGS' in bld
.env
:
679 list = bld
.env
['EXTRA_CFLAGS'];
680 ret
= TO_LIST(cflags
)
682 if hide_symbols
and bld
.env
.HAVE_VISIBILITY_ATTR
:
683 ret
.append('-fvisibility=hidden')
688 def CHECK_CC_ENV(conf
):
689 """trim whitespaces from 'CC'.
690 The build farm sometimes puts a space at the start"""
691 if os
.environ
.get('CC'):
692 conf
.env
.CC
= TO_LIST(os
.environ
.get('CC'))
693 if len(conf
.env
.CC
) == 1:
694 # make for nicer logs if just a single command
695 conf
.env
.CC
= conf
.env
.CC
[0]
699 def SETUP_CONFIGURE_CACHE(conf
, enable
):
700 '''enable/disable cache of configure results'''
702 # when -C is chosen, we will use a private cache and will
703 # not look into system includes. This roughtly matches what
704 # autoconf does with -C
705 cache_path
= os
.path
.join(conf
.blddir
, '.confcache')
707 Options
.cache_global
= os
.environ
['WAFCACHE'] = cache_path
709 # when -C is not chosen we will not cache configure checks
710 # We set the recursion limit low to prevent waf from spending
711 # a lot of time on the signatures of the files.
712 Options
.cache_global
= os
.environ
['WAFCACHE'] = ''
713 preproc
.recursion_limit
= 1
714 # in either case we don't need to scan system includes
715 preproc
.go_absolute
= False