wafsamba: allow cflags for CHECK_TYPE[_IN]()
[samba.git] / buildtools / wafsamba / samba_autoconf.py
index be179d8b29bae8e0fb39d59a7fb29a52cc3d150b..3ca2f33419010a737440861ce0a1de2a1396ec87 100644 (file)
@@ -23,13 +23,12 @@ def DEFINE(conf, d, v, add_to_cflags=False, quote=False):
 
 def hlist_to_string(conf, headers=None):
     '''convert a headers list to a set of #include lines'''
-    hdrs=''
     hlist = conf.env.hlist
     if headers:
         hlist = hlist[:]
         hlist.extend(TO_LIST(headers))
-    for h in hlist:
-        hdrs += '#include <%s>\n' % h
+    hdrs = "\n".join('#include <%s>' % h for h in hlist)
+
     return hdrs
 
 
@@ -147,7 +146,7 @@ def header_list(conf, headers=None, lib=None):
 
 
 @conf
-def CHECK_TYPE(conf, t, alternate=None, headers=None, define=None, lib=None, msg=None):
+def CHECK_TYPE(conf, t, alternate=None, headers=None, define=None, lib=None, msg=None, cflags=''):
     '''check for a single type'''
     if define is None:
         define = 'HAVE_' + t.upper().replace(' ', '_')
@@ -159,6 +158,7 @@ def CHECK_TYPE(conf, t, alternate=None, headers=None, define=None, lib=None, msg
                      headers=headers,
                      local_include=False,
                      msg=msg,
+                     cflags=cflags,
                      lib=lib,
                      link=False)
     if not ret and alternate:
@@ -178,9 +178,9 @@ def CHECK_TYPES(conf, list, headers=None, define=None, alternate=None, lib=None)
 
 
 @conf
-def CHECK_TYPE_IN(conf, t, headers=None, alternate=None, define=None):
+def CHECK_TYPE_IN(conf, t, headers=None, alternate=None, define=None, cflags=''):
     '''check for a single type with a header'''
-    return CHECK_TYPE(conf, t, headers=headers, alternate=alternate, define=define)
+    return CHECK_TYPE(conf, t, headers=headers, alternate=alternate, define=define, cflags=cflags)
 
 
 @conf
@@ -213,7 +213,7 @@ def CHECK_VARIABLE(conf, v, define=None, always=False,
 
 
 @conf
-def CHECK_DECLS(conf, vars, reverse=False, headers=None, always=False):
+def CHECK_DECLS(conf, vars, reverse=False, headers=None, lib=None, always=False):
     '''check a list of variable declarations, using the HAVE_DECL_xxx form
        of define
 
@@ -228,6 +228,7 @@ def CHECK_DECLS(conf, vars, reverse=False, headers=None, always=False):
         if not CHECK_VARIABLE(conf, v,
                               define=define,
                               headers=headers,
+                              lib=lib,
                               msg='Checking for declaration of %s' % v,
                               always=always):
             if not CHECK_CODE(conf,
@@ -239,6 +240,7 @@ def CHECK_DECLS(conf, vars, reverse=False, headers=None, always=False):
                       msg='Checking for declaration of %s (as enum)' % v,
                       local_include=False,
                       headers=headers,
+                      lib=lib,
                       define=define,
                       always=always):
                 ret = False
@@ -342,6 +344,23 @@ def CHECK_SIZEOF(conf, vars, headers=None, define=None, critical=True):
             sys.exit(1)
     return ret
 
+@conf
+def CHECK_SIGN(conf, v, headers=None):
+    '''check the sign of a type'''
+    define_name = v.upper().replace(' ', '_')
+    for op, signed in [('<', 'signed'),
+                       ('>', 'unsigned')]:
+        if CHECK_CODE(conf,
+                      f'static int test_array[1 - 2 * !((({v})-1) {op} 0)];',
+                      define=f'{define_name}_{signed.upper()}',
+                      quote=False,
+                      headers=headers,
+                      local_include=False,
+                      msg=f"Checking if '{v}' is {signed}"):
+            return True
+
+    return False
+
 @conf
 def CHECK_VALUEOF(conf, v, headers=None, define=None):
     '''check the value of a variable/define'''
@@ -423,9 +442,9 @@ def CHECK_CODE(conf, code, define,
     cflags.extend(ccflags)
 
     if on_target:
-        exec_args = conf.SAMBA_CROSS_ARGS(msg=msg)
+        test_args = conf.SAMBA_CROSS_ARGS(msg=msg)
     else:
-        exec_args = []
+        test_args = []
 
     conf.COMPOUND_START(msg)
 
@@ -440,7 +459,7 @@ def CHECK_CODE(conf, code, define,
                      type=type,
                      msg=msg,
                      quote=quote,
-                     exec_args=exec_args,
+                     test_args=test_args,
                      define_ret=define_ret)
     except Exception:
         if always:
@@ -488,7 +507,8 @@ def CHECK_STRUCTURE_MEMBER(conf, structname, member,
 
 
 @conf
-def CHECK_CFLAGS(conf, cflags, fragment='int main(void) { return 0; }\n'):
+def CHECK_CFLAGS(conf, cflags, fragment='int main(void) { return 0; }\n',
+                 mandatory=False):
     '''check if the given cflags are accepted by the compiler
     '''
     check_cflags = TO_LIST(cflags)
@@ -496,19 +516,20 @@ def CHECK_CFLAGS(conf, cflags, fragment='int main(void) { return 0; }\n'):
         check_cflags.extend(conf.env['WERROR_CFLAGS'])
     return conf.check(fragment=fragment,
                       execute=0,
-                      mandatory=False,
+                      mandatory=mandatory,
                       type='nolink',
                       cflags=check_cflags,
                       msg="Checking compiler accepts %s" % cflags)
 
 @conf
-def CHECK_LDFLAGS(conf, ldflags):
+def CHECK_LDFLAGS(conf, ldflags,
+                  mandatory=False):
     '''check if the given ldflags are accepted by the linker
     '''
     return conf.check(fragment='int main(void) { return 0; }\n',
                       execute=0,
                       ldflags=ldflags,
-                      mandatory=False,
+                      mandatory=mandatory,
                       msg="Checking linker accepts %s" % ldflags)
 
 
@@ -724,6 +745,9 @@ def SAMBA_CONFIG_H(conf, path=None):
     if Options.options.debug:
         conf.ADD_CFLAGS('-g', testflags=True)
 
+    if Options.options.pidl_developer:
+        conf.env.PIDL_DEVELOPER_MODE = True
+
     if Options.options.developer:
         conf.env.DEVELOPER_MODE = True
 
@@ -783,9 +807,13 @@ int main(void) {
                 conf.env['EXTRA_CFLAGS'] = []
             conf.env['EXTRA_CFLAGS'].extend(TO_LIST("-Werror=format"))
 
-    if Options.options.picky_developer:
-        conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Werror -Wno-error=deprecated-declarations', testflags=True)
-        conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Wno-error=tautological-compare', testflags=True)
+        if CHECK_CFLAGS(conf, ["-Wno-error=array-bounds"]):
+            conf.define('HAVE_WNO_ERROR_ARRAY_BOUNDS', 1)
+
+        if not Options.options.disable_warnings_as_errors:
+            conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Werror -Wno-error=deprecated-declarations', testflags=True)
+            conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Wno-error=tautological-compare', testflags=True)
+            conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Wno-error=cast-align', testflags=True)
 
     if Options.options.fatal_errors:
         conf.ADD_CFLAGS('-Wfatal-errors', testflags=True)
@@ -795,13 +823,16 @@ int main(void) {
 
     if (Options.options.address_sanitizer or
         Options.options.undefined_sanitizer):
-        conf.ADD_CFLAGS('-fno-omit-frame-pointer -O1', testflags=True)
+        conf.ADD_CFLAGS('-g -O1', testflags=True)
     if Options.options.address_sanitizer:
+        conf.ADD_CFLAGS('-fno-omit-frame-pointer', testflags=True)
         conf.ADD_CFLAGS('-fsanitize=address', testflags=True)
         conf.ADD_LDFLAGS('-fsanitize=address', testflags=True)
         conf.env['ADDRESS_SANITIZER'] = True
     if Options.options.undefined_sanitizer:
         conf.ADD_CFLAGS('-fsanitize=undefined', testflags=True)
+        conf.ADD_CFLAGS('-fsanitize=null', testflags=True)
+        conf.ADD_CFLAGS('-fsanitize=alignment', testflags=True)
         conf.ADD_LDFLAGS('-fsanitize=undefined', testflags=True)
         conf.env['UNDEFINED_SANITIZER'] = True
 
@@ -811,11 +842,19 @@ int main(void) {
     #
     # The CFLAGS and LDFLAGS environment variables are also
     # used for the configure checks which might impact their results.
+    #
+    # If these variables don't pass a smoke test, fail the configure
+
     conf.add_os_flags('ADDITIONAL_CFLAGS')
-    if conf.env.ADDITIONAL_CFLAGS and conf.CHECK_CFLAGS(conf.env['ADDITIONAL_CFLAGS']):
+    if conf.env.ADDITIONAL_CFLAGS:
+        conf.CHECK_CFLAGS(conf.env['ADDITIONAL_CFLAGS'],
+                          mandatory=True)
         conf.env['EXTRA_CFLAGS'].extend(conf.env['ADDITIONAL_CFLAGS'])
+
     conf.add_os_flags('ADDITIONAL_LDFLAGS')
-    if conf.env.ADDITIONAL_LDFLAGS and conf.CHECK_LDFLAGS(conf.env['ADDITIONAL_LDFLAGS']):
+    if conf.env.ADDITIONAL_LDFLAGS:
+        conf.CHECK_LDFLAGS(conf.env['ADDITIONAL_LDFLAGS'],
+                           mandatory=True)
         conf.env['EXTRA_LDFLAGS'].extend(conf.env['ADDITIONAL_LDFLAGS'])
 
     if path is None:
@@ -889,9 +928,15 @@ def ADD_EXTRA_INCLUDES(conf, includes):
 
 
 
-def CURRENT_CFLAGS(bld, target, cflags, allow_warnings=False, hide_symbols=False):
+def CURRENT_CFLAGS(bld, target, cflags,
+                   allow_warnings=False,
+                   use_hostcc=False,
+                   hide_symbols=False):
     '''work out the current flags. local flags are added first'''
-    ret = TO_LIST(cflags)
+    ret = []
+    if use_hostcc:
+        ret += ['-D_SAMBA_HOSTCC_']
+    ret += TO_LIST(cflags)
     if not 'EXTRA_CFLAGS' in bld.env:
         list = []
     else:
@@ -935,6 +980,11 @@ def SETUP_CONFIGURE_CACHE(conf, enable):
 
 @conf
 def SAMBA_CHECK_UNDEFINED_SYMBOL_FLAGS(conf):
+    if Options.options.address_sanitizer or Options.options.enable_libfuzzer:
+        # Sanitizers can rely on symbols undefined at library link time and the
+        # symbols used for fuzzers are only defined by compiler wrappers.
+        return
+
     if not sys.platform.startswith("openbsd"):
         # we don't want any libraries or modules to rely on runtime
         # resolution of symbols