Imported Upstream version 2.1.2
authorJelmer Vernooij <jelmer@debian.org>
Sun, 15 Mar 2015 01:56:53 +0000 (02:56 +0100)
committerJelmer Vernooij <jelmer@debian.org>
Sun, 15 Mar 2015 01:56:53 +0000 (02:56 +0100)
32 files changed:
ABI/pytalloc-util-2.1.2.sigs [new file with mode: 0644]
ABI/talloc-2.1.2.sigs [new file with mode: 0644]
buildtools/wafadmin/Tools/ccroot.py
buildtools/wafadmin/Tools/gcc.py
buildtools/wafadmin/Tools/gxx.py
buildtools/wafadmin/Tools/perl.py
buildtools/wafsamba/samba3.py
buildtools/wafsamba/samba_autoconf.py
buildtools/wafsamba/samba_bundled.py
buildtools/wafsamba/samba_conftests.py
buildtools/wafsamba/samba_deps.py
buildtools/wafsamba/samba_dist.py
buildtools/wafsamba/samba_optimisation.py
buildtools/wafsamba/samba_patterns.py
buildtools/wafsamba/samba_perl.py [new file with mode: 0644]
buildtools/wafsamba/samba_third_party.py [new file with mode: 0644]
buildtools/wafsamba/samba_utils.py
buildtools/wafsamba/test_duplicate_symbol.sh [new file with mode: 0755]
buildtools/wafsamba/wafsamba.py
buildtools/wafsamba/wscript
lib/replace/replace.h
lib/replace/snprintf.c
lib/replace/system/filesys.h
lib/replace/system/network.h
lib/replace/system/passwd.h
lib/replace/system/select.h
lib/replace/system/threads.h [new file with mode: 0644]
lib/replace/test/os2_delete.c
lib/replace/wscript
talloc.c
testsuite.c
wscript

diff --git a/ABI/pytalloc-util-2.1.2.sigs b/ABI/pytalloc-util-2.1.2.sigs
new file mode 100644 (file)
index 0000000..961c1a8
--- /dev/null
@@ -0,0 +1,6 @@
+pytalloc_CObject_FromTallocPtr: PyObject *(void *)
+pytalloc_Check: int (PyObject *)
+pytalloc_GetObjectType: PyTypeObject *(void)
+pytalloc_reference_ex: PyObject *(PyTypeObject *, TALLOC_CTX *, void *)
+pytalloc_steal: PyObject *(PyTypeObject *, void *)
+pytalloc_steal_ex: PyObject *(PyTypeObject *, TALLOC_CTX *, void *)
diff --git a/ABI/talloc-2.1.2.sigs b/ABI/talloc-2.1.2.sigs
new file mode 100644 (file)
index 0000000..eae12cc
--- /dev/null
@@ -0,0 +1,64 @@
+_talloc: void *(const void *, size_t)
+_talloc_array: void *(const void *, size_t, unsigned int, const char *)
+_talloc_free: int (void *, const char *)
+_talloc_get_type_abort: void *(const void *, const char *, const char *)
+_talloc_memdup: void *(const void *, const void *, size_t, const char *)
+_talloc_move: void *(const void *, const void *)
+_talloc_pooled_object: void *(const void *, size_t, const char *, unsigned int, size_t)
+_talloc_realloc: void *(const void *, void *, size_t, const char *)
+_talloc_realloc_array: void *(const void *, void *, size_t, unsigned int, const char *)
+_talloc_reference_loc: void *(const void *, const void *, const char *)
+_talloc_set_destructor: void (const void *, int (*)(void *))
+_talloc_steal_loc: void *(const void *, const void *, const char *)
+_talloc_zero: void *(const void *, size_t, const char *)
+_talloc_zero_array: void *(const void *, size_t, unsigned int, const char *)
+talloc_asprintf: char *(const void *, const char *, ...)
+talloc_asprintf_append: char *(char *, const char *, ...)
+talloc_asprintf_append_buffer: char *(char *, const char *, ...)
+talloc_autofree_context: void *(void)
+talloc_check_name: void *(const void *, const char *)
+talloc_disable_null_tracking: void (void)
+talloc_enable_leak_report: void (void)
+talloc_enable_leak_report_full: void (void)
+talloc_enable_null_tracking: void (void)
+talloc_enable_null_tracking_no_autofree: void (void)
+talloc_find_parent_byname: void *(const void *, const char *)
+talloc_free_children: void (void *)
+talloc_get_name: const char *(const void *)
+talloc_get_size: size_t (const void *)
+talloc_increase_ref_count: int (const void *)
+talloc_init: void *(const char *, ...)
+talloc_is_parent: int (const void *, const void *)
+talloc_named: void *(const void *, size_t, const char *, ...)
+talloc_named_const: void *(const void *, size_t, const char *)
+talloc_parent: void *(const void *)
+talloc_parent_name: const char *(const void *)
+talloc_pool: void *(const void *, size_t)
+talloc_realloc_fn: void *(const void *, void *, size_t)
+talloc_reference_count: size_t (const void *)
+talloc_reparent: void *(const void *, const void *, const void *)
+talloc_report: void (const void *, FILE *)
+talloc_report_depth_cb: void (const void *, int, int, void (*)(const void *, int, int, int, void *), void *)
+talloc_report_depth_file: void (const void *, int, int, FILE *)
+talloc_report_full: void (const void *, FILE *)
+talloc_set_abort_fn: void (void (*)(const char *))
+talloc_set_log_fn: void (void (*)(const char *))
+talloc_set_log_stderr: void (void)
+talloc_set_memlimit: int (const void *, size_t)
+talloc_set_name: const char *(const void *, const char *, ...)
+talloc_set_name_const: void (const void *, const char *)
+talloc_show_parents: void (const void *, FILE *)
+talloc_strdup: char *(const void *, const char *)
+talloc_strdup_append: char *(char *, const char *)
+talloc_strdup_append_buffer: char *(char *, const char *)
+talloc_strndup: char *(const void *, const char *, size_t)
+talloc_strndup_append: char *(char *, const char *, size_t)
+talloc_strndup_append_buffer: char *(char *, const char *, size_t)
+talloc_total_blocks: size_t (const void *)
+talloc_total_size: size_t (const void *)
+talloc_unlink: int (const void *, void *)
+talloc_vasprintf: char *(const void *, const char *, va_list)
+talloc_vasprintf_append: char *(char *, const char *, va_list)
+talloc_vasprintf_append_buffer: char *(char *, const char *, va_list)
+talloc_version_major: int (void)
+talloc_version_minor: int (void)
index 264bdc7f0f6350db145fcdcba22aff27a94b306a..25c5179be0e08581c75024fafcaff0a71d22a724 100644 (file)
@@ -177,10 +177,16 @@ def get_target_name(self):
 
        dir, name = os.path.split(self.target)
 
-       if self.env.DEST_BINFMT == 'pe' and getattr(self, 'vnum', None) and 'cshlib' in self.features:
-               # include the version in the dll file name,
-               # the import lib file name stays unversionned.
-               name = name + '-' + self.vnum.split('.')[0]
+       if 'cshlib' in self.features and getattr(self, 'vnum', None):
+               nums = self.vnum.split('.')
+               if self.env.DEST_BINFMT == 'pe':
+                       # include the version in the dll file name,
+                       # the import lib file name stays unversionned.
+                       name = name + '-' + nums[0]
+               elif self.env.DEST_OS == 'openbsd':
+                       pattern = '%s.%s' % (pattern, nums[0])
+                       if len(nums) >= 2:
+                               pattern += '.%s' % nums[1]
 
        return os.path.join(dir, pattern % name)
 
@@ -598,14 +604,16 @@ def apply_vnum(self):
        if not path: return
 
        if self.env.DEST_OS == 'openbsd':
-               bld.install_as(path + os.sep + name2, node, env=self.env, chmod=self.link_task.chmod)
+               libname = self.link_task.outputs[0].name
+               bld.install_as('%s%s%s' % (path, os.sep, libname), node, env=self.env)
        else:
                bld.install_as(path + os.sep + name3, node, env=self.env)
                bld.symlink_as(path + os.sep + name2, name3)
                bld.symlink_as(path + os.sep + libname, name3)
 
        # the following task is just to enable execution from the build dir :-/
-       self.create_task('vnum', node, [node.parent.find_or_declare(name2), node.parent.find_or_declare(name3)])
+       if self.env.DEST_OS != 'openbsd':
+               self.create_task('vnum', node, [node.parent.find_or_declare(name2), node.parent.find_or_declare(name3)])
 
 def exec_vnum_link(self):
        for x in self.outputs:
index 420b44fd8f20f8caa697c35410be514989927c6e..a6be0b28dbf133097d69798d5bc7eefc92af4c16 100644 (file)
@@ -113,6 +113,10 @@ def gcc_modifier_aix(conf):
 
        v['SHLIB_MARKER']        = ''
 
+@conftest
+def gcc_modifier_openbsd(conf):
+       conf.env['SONAME_ST'] = []
+
 @conftest
 def gcc_modifier_platform(conf):
        # * set configurations specific for a platform.
index 8f4a0bfef0668fb9d7050b167fd4a29dea151953..4984122e5e6239cb2e462fbca06dd710f134432c 100644 (file)
@@ -111,6 +111,10 @@ def gxx_modifier_aix(conf):
 
        v['SHLIB_MARKER']        = ''
 
+@conftest
+def gxx_modifier_openbsd(conf):
+       conf.env['SONAME_ST'] = []
+
 @conftest
 def gxx_modifier_platform(conf):
        # * set configurations specific for a platform.
index 0f34e79aa399ce78a8cda2502fb3ba161e1e65c6..a6787a86ecfa86d41593fb01c561e145d6825738 100644 (file)
@@ -98,53 +98,12 @@ def check_perl_ext_devel(conf):
        conf.env.EXTUTILS_TYPEMAP  = read_out('print "$Config{privlib}/ExtUtils/typemap"')
        conf.env.perlext_PATTERN   = '%s.' + read_out('print $Config{dlext}')[0]
 
-       def try_any(keys):
-               for k in keys:
-                       conf.start_msg("Checking for perl $Config{%s}:" % k)
-                       try:
-                               v = read_out('print $Config{%s}' % k)[0]
-                               conf.end_msg("'%s'" % (v), 'GREEN')
-                               return v
-                       except IndexError:
-                               conf.end_msg(False, 'YELLOW')
-                               pass
-               return None
-
-       perl_arch_install_dir = None
-       if getattr(Options.options, 'perl_arch_install_dir', None):
-               perl_arch_install_dir = Options.options.perl_arch_install_dir
-       if perl_arch_install_dir is None:
-               perl_arch_install_dir = try_any(['vendorarch', 'sitearch', 'archlib'])
-       if perl_arch_install_dir is None:
-               conf.fatal('No perl arch install directory autodetected.' +
-                          'Please define it with --with-perl-arch-install-dir.')
-       conf.start_msg("PERL_ARCH_INSTALL_DIR: ")
-       conf.end_msg("'%s'" % (perl_arch_install_dir), 'GREEN')
-       conf.env.PERL_ARCH_INSTALL_DIR = perl_arch_install_dir
-
-       perl_lib_install_dir = None
-       if getattr(Options.options, 'perl_lib_install_dir', None):
-               perl_lib_install_dir = Options.options.perl_lib_install_dir
-       if perl_lib_install_dir is None:
-               perl_lib_install_dir = try_any(['vendorlib', 'sitelib', 'privlib'])
-       if perl_lib_install_dir is None:
-               conf.fatal('No perl lib install directory autodetected. ' +
-                          'Please define it with --with-perl-lib-install-dir.')
-       conf.start_msg("PERL_LIB_INSTALL_DIR: ")
-       conf.end_msg("'%s'" % (perl_lib_install_dir), 'GREEN')
-       conf.env.PERL_LIB_INSTALL_DIR = perl_lib_install_dir
+       if getattr(Options.options, 'perlarchdir', None):
+               conf.env.ARCHDIR_PERL = Options.options.perlarchdir
+       else:
+               conf.env.ARCHDIR_PERL = read_out('print $Config{sitearch}')[0]
 
 def set_options(opt):
        opt.add_option("--with-perl-binary", type="string", dest="perlbinary", help = 'Specify alternate perl binary', default=None)
+       opt.add_option("--with-perl-archdir", type="string", dest="perlarchdir", help = 'Specify directory where to install arch specific files', default=None)
 
-       opt.add_option("--with-perl-arch-install-dir",
-                      type="string",
-                      dest="perl_arch_install_dir",
-                      help = ('Specify directory where to install arch specific files'),
-                      default=None)
-
-       opt.add_option("--with-perl-lib-install-dir",
-                      type="string",
-                      dest="perl_lib_install_dir",
-                      help = ('Specify directory where to install vendor specific files'),
-                      default=None)
index fd063ad8c472a09d44835a0f1ee241aff28d388b..ffe678416edfb457a92b200530c9b3c2bc7193e0 100644 (file)
@@ -6,16 +6,17 @@ from optparse import SUPPRESS_HELP
 from samba_utils import os_path_relpath, TO_LIST
 from samba_autoconf import library_flags
 
+
 def SAMBA3_ADD_OPTION(opt, option, help=(), dest=None, default=True,
                       with_name="with", without_name="without"):
     if default is None:
-        default_str="auto"
-    elif default == True:
-        default_str="yes"
-    elif default == False:
-        default_str="no"
+        default_str = "auto"
+    elif default is True:
+        default_str = "yes"
+    elif default is False:
+        default_str = "no"
     else:
-        default_str=str(default)
+        default_str = str(default)
 
     if help == ():
         help = ("Build with %s support (default=%s)" % (option, default_str))
@@ -94,12 +95,6 @@ def s3_fix_kwargs(bld, kwargs):
     else:
         extra_includes += [ '../lib/popt' ]
 
-    if bld.CONFIG_SET('USING_SYSTEM_INIPARSER'):
-        (iniparser_includes, iniparser_ldflags, iniparser_cpppath) = library_flags(bld, 'iniparser')
-        extra_includes += iniparser_cpppath
-    else:
-        extra_includes += [ '../lib/iniparser' ]
-
     # s3 builds assume that they will have a bunch of extra include paths
     includes = []
     for d in extra_includes:
index f60ce9dc2ba7d40f09812ee517fd97ce4d0a61b6..905adc7df6413e0bf8bf1d9bc0daa0a482bb9884 100644 (file)
@@ -646,6 +646,10 @@ def SAMBA_CONFIG_H(conf, path=None):
     if not IN_LAUNCH_DIR(conf):
         return
 
+    if conf.CHECK_CFLAGS(['-fstack-protector']) and conf.CHECK_LDFLAGS(['-fstack-protector']):
+        conf.ADD_CFLAGS('-fstack-protector')
+        conf.ADD_LDFLAGS('-fstack-protector')
+
     if Options.options.debug:
         conf.ADD_CFLAGS('-g', testflags=True)
 
@@ -671,6 +675,10 @@ def SAMBA_CONFIG_H(conf, path=None):
                         testflags=True)
         conf.ADD_CFLAGS('-Werror=declaration-after-statement -Wdeclaration-after-statement',
                         testflags=True)
+        conf.ADD_CFLAGS('-Werror=return-type -Wreturn-type',
+                        testflags=True)
+        conf.ADD_CFLAGS('-Werror=uninitialized -Wuninitialized',
+                        testflags=True)
 
         conf.ADD_CFLAGS('-Wformat=2 -Wno-format-y2k', testflags=True)
         # This check is because for ldb_search(), a NULL format string
@@ -689,7 +697,7 @@ int main(void) {
             conf.env['EXTRA_CFLAGS'].extend(TO_LIST("-Werror=format"))
 
     if Options.options.picky_developer:
-        conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Werror', testflags=True)
+        conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Werror -Wno-error=deprecated-declarations', testflags=True)
 
     if Options.options.fatal_errors:
         conf.ADD_CFLAGS('-Wfatal-errors', testflags=True)
@@ -697,6 +705,24 @@ int main(void) {
     if Options.options.pedantic:
         conf.ADD_CFLAGS('-W', testflags=True)
 
+    if Options.options.address_sanitizer:
+        conf.ADD_CFLAGS('-fno-omit-frame-pointer -O1 -fsanitize=address', testflags=True)
+        conf.ADD_LDFLAGS('-fsanitize=address', testflags=True)
+        conf.env['ADDRESS_SANITIZER'] = True
+
+
+    # Let people pass an additional ADDITIONAL_{CFLAGS,LDFLAGS}
+    # environment variables which are only used the for final build.
+    #
+    # The CFLAGS and LDFLAGS environment variables are also
+    # used for the configure checks which might impact their results.
+    conf.add_os_flags('ADDITIONAL_CFLAGS')
+    if conf.env.ADDITIONAL_CFLAGS and conf.CHECK_CFLAGS(conf.env['ADDITIONAL_CFLAGS']):
+        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']):
+        conf.env['EXTRA_LDFLAGS'].extend(conf.env['ADDITIONAL_LDFLAGS'])
+
     if path is None:
         conf.write_config_header('config.h', top=True)
     else:
@@ -763,7 +789,7 @@ def ADD_EXTRA_INCLUDES(conf, includes):
 
 
 
-def CURRENT_CFLAGS(bld, target, cflags, allow_warnings=True, hide_symbols=False):
+def CURRENT_CFLAGS(bld, target, cflags, allow_warnings=False, hide_symbols=False):
     '''work out the current flags. local flags are added first'''
     ret = TO_LIST(cflags)
     if not 'EXTRA_CFLAGS' in bld.env:
@@ -775,7 +801,7 @@ def CURRENT_CFLAGS(bld, target, cflags, allow_warnings=True, hide_symbols=False)
         list = bld.env['PICKY_CFLAGS'];
         ret.extend(list)
     if hide_symbols and bld.env.HAVE_VISIBILITY_ATTR:
-        ret.append('-fvisibility=hidden')
+        ret.append(bld.env.VISIBILITY_CFLAGS)
     return ret
 
 
index 45946d524bf12b959ea0500f816d4b834ef3e1de..515590fb01468a1d9218705d8644e661487f205d 100644 (file)
@@ -7,11 +7,25 @@ from samba_utils import *
 def PRIVATE_NAME(bld, name, private_extension, private_library):
     '''possibly rename a library to include a bundled extension'''
 
+    if not private_library:
+        return name
+
     # we now use the same private name for libraries as the public name.
     # see http://git.samba.org/?p=tridge/junkcode.git;a=tree;f=shlib for a
     # demonstration that this is the right thing to do
     # also see http://lists.samba.org/archive/samba-technical/2011-January/075816.html
-    return name
+    if private_extension:
+        return name
+
+    extension = bld.env.PRIVATE_EXTENSION
+
+    if extension and name.startswith('%s' % extension):
+        return name
+
+    if extension and name.endswith('%s' % extension):
+        return name
+
+    return "%s-%s" % (name, extension)
 
 
 def target_in_list(target, lst, default):
index ec98ba0d7eea550aa95aee37aa8d9f8283b1db43..1afc6c94fbe817d89043f2f806208995f11efcca 100644 (file)
@@ -4,6 +4,7 @@
 import os, shutil, re
 import Build, Configure, Utils
 from Configure import conf
+import config_c
 from samba_utils import *
 
 
@@ -506,3 +507,84 @@ def CHECK_XSLTPROC_MANPAGES(conf):
     if not conf.CONFIG_SET('XSLTPROC_MANPAGES'):
         print "A local copy of the docbook.xsl wasn't found on your system" \
               " consider installing package like docbook-xsl"
+
+#
+# Determine the standard libpath for the used compiler,
+# so we can later use that to filter out these standard
+# library paths when some tools like cups-config or
+# python-config report standard lib paths with their
+# ldflags (-L...)
+#
+@conf
+def CHECK_STANDARD_LIBPATH(conf):
+    # at least gcc and clang support this:
+    try:
+        cmd = conf.env.CC + ['-print-search-dirs']
+        out = Utils.cmd_output(cmd).split('\n')
+    except ValueError:
+        # option not supported by compiler - use a standard list of directories
+        dirlist = [ '/usr/lib', '/usr/lib64' ]
+    except:
+        raise Utils.WafError('Unexpected error running "%s"' % (cmd))
+    else:
+        dirlist = []
+        for line in out:
+            line = line.strip()
+            if line.startswith("libraries: ="):
+                dirliststr = line[len("libraries: ="):]
+                dirlist = [ os.path.normpath(x) for x in dirliststr.split(':') ]
+                break
+
+    conf.env.STANDARD_LIBPATH = dirlist
+
+
+waf_config_c_parse_flags = config_c.parse_flags;
+def samba_config_c_parse_flags(line1, uselib, env):
+    #
+    # We do a special treatment of the rpath components
+    # in the linkflags line, because currently the upstream
+    # parse_flags function is incomplete with respect to
+    # treatment of the rpath. The remainder of the linkflags
+    # line is later passed to the original funcion.
+    #
+    lst1 = shlex.split(line1)
+    lst2 = []
+    while lst1:
+        x = lst1.pop(0)
+
+        #
+        # NOTE on special treatment of -Wl,-R and -Wl,-rpath:
+        #
+        # It is important to not put a library provided RPATH
+        # into the LINKFLAGS but in the RPATH instead, since
+        # the provided LINKFLAGS get prepended to our own internal
+        # RPATH later, and hence can potentially lead to linking
+        # in too old versions of our internal libs.
+        #
+        # We do this filtering here on our own because of some
+        # bugs in the real parse_flags() function.
+        #
+        if x == '-Wl,-rpath' or x == '-Wl,-R':
+            linkflags.remove(x)
+            x = lst1.pop(0)
+            if x.startswith('-Wl,'):
+                rpath = x[4:]
+            else:
+                rpath = x
+        elif x.startswith('-Wl,-R,'):
+            rpath = x[7:]
+        elif x.startswith('-Wl,-R'):
+            rpath = x[6:]
+        elif x.startswith('-Wl,-rpath,'):
+            rpath = x[11:]
+        else:
+            lst2.append(x)
+            continue
+
+        env.append_value('RPATH_' + uselib, rpath)
+
+    line2 = ' '.join(lst2)
+    waf_config_c_parse_flags(line2, uselib, env)
+
+    return
+config_c.parse_flags = samba_config_c_parse_flags
index c00744ea7a66e8821d0318ae128d748a5a56e822..3be99565a664aa55359b57e5fb52c8fa4a8dbee5 100644 (file)
@@ -1021,7 +1021,7 @@ def save_samba_deps(bld, tgt_list):
             denv.outenv[t.sname] = tdeps
 
     depsfile = os.path.join(bld.bdir, "sambadeps")
-    denv.store(depsfile)
+    denv.store_fast(depsfile)
 
 
 
@@ -1031,12 +1031,12 @@ def load_samba_deps(bld, tgt_list):
     denv = Environment.Environment()
     try:
         debug('deps: checking saved dependencies')
-        denv.load(depsfile)
+        denv.load_fast(depsfile)
         if (denv.version != savedeps_version or
             denv.savedeps_inputs != savedeps_inputs or
             denv.savedeps_outputs != savedeps_outputs):
             return False
-    except:
+    except Exception:
         return False
 
     # check if critical files have changed
index fae2759dac0d6d6646c5c81117b591d943f3f8ed..aecacb7fd15f2355ac59a4124ba8392f4f12c3cd 100644 (file)
@@ -127,11 +127,14 @@ def dist(appname='', version=''):
             add_tarfile(tar, fname, abspath, srcsubdir)
 
 
-    def list_directory_files(abspath):
+    def list_directory_files(path):
+        curdir = os.getcwd()
+        os.chdir(srcdir)
         out_files = []
-        for root, dirs, files in os.walk(abspath):
+        for root, dirs, files in os.walk(path):
             for f in files:
                 out_files.append(os.path.join(root, f))
+        os.chdir(curdir)
         return out_files
 
 
index f0f430d2bfdb6f35d334e34961d9b29b2dfd7d33..5def5803804ce9e4b809c7af406abe490b0820a3 100644 (file)
@@ -6,8 +6,10 @@
 
 # overall this makes some build tasks quite a bit faster
 
-from TaskGen import feature, after
-import preproc, Task
+import os
+import Build, Utils, Node
+from TaskGen import feature, after, before
+import preproc
 
 @feature('cc', 'cxx')
 @after('apply_type_vars', 'apply_lib_vars', 'apply_core')
@@ -122,44 +124,208 @@ def hash_constraints(self):
     return sum
 Task.TaskBase.hash_constraints = hash_constraints
 
+def hash_env_vars(self, env, vars_lst):
+    idx = str(id(env)) + str(vars_lst)
+    try:
+        return self.cache_sig_vars[idx]
+    except KeyError:
+        pass
+
+    m = Utils.md5()
+    m.update(''.join([str(env[a]) for a in vars_lst]))
+
+    ret = self.cache_sig_vars[idx] = m.digest()
+    return ret
+Build.BuildContext.hash_env_vars = hash_env_vars
+
+
+def store_fast(self, filename):
+    file = open(filename, 'wb')
+    data = self.get_merged_dict()
+    try:
+        Build.cPickle.dump(data, file, -1)
+    finally:
+        file.close()
+Environment.Environment.store_fast = store_fast
+
+def load_fast(self, filename):
+    file = open(filename, 'rb')
+    try:
+        data = Build.cPickle.load(file)
+    finally:
+        file.close()
+    self.table.update(data)
+Environment.Environment.load_fast = load_fast
+
+def is_this_a_static_lib(self, name):
+    try:
+        cache = self.cache_is_this_a_static_lib
+    except AttributeError:
+        cache = self.cache_is_this_a_static_lib = {}
+    try:
+        return cache[name]
+    except KeyError:
+        ret = cache[name] = 'cstaticlib' in self.bld.name_to_obj(name, self.env).features
+        return ret
+TaskGen.task_gen.is_this_a_static_lib = is_this_a_static_lib
+
+def shared_ancestors(self):
+    try:
+        cache = self.cache_is_this_a_static_lib
+    except AttributeError:
+        cache = self.cache_is_this_a_static_lib = {}
+    try:
+        return cache[id(self)]
+    except KeyError:
+
+        ret = []
+        if 'cshlib' in self.features: # or 'cprogram' in self.features:
+            if getattr(self, 'uselib_local', None):
+                lst = self.to_list(self.uselib_local)
+                ret = [x for x in lst if not self.is_this_a_static_lib(x)]
+        cache[id(self)] = ret
+        return ret
+TaskGen.task_gen.shared_ancestors = shared_ancestors
+
+@feature('cc', 'cxx')
+@after('apply_link', 'init_cc', 'init_cxx', 'apply_core')
+def apply_lib_vars(self):
+    """after apply_link because of 'link_task'
+    after default_cc because of the attribute 'uselib'"""
+
+    # after 'apply_core' in case if 'cc' if there is no link
+
+    env = self.env
+    app = env.append_value
+    seen_libpaths = set([])
+
+    # OPTIMIZATION 1: skip uselib variables already added (700ms)
+    seen_uselib = set([])
+
+    # 1. the case of the libs defined in the project (visit ancestors first)
+    # the ancestors external libraries (uselib) will be prepended
+    self.uselib = self.to_list(self.uselib)
+    names = self.to_list(self.uselib_local)
+
+    seen = set([])
+    tmp = Utils.deque(names) # consume a copy of the list of names
+    while tmp:
+        lib_name = tmp.popleft()
+        # visit dependencies only once
+        if lib_name in seen:
+            continue
+
+        y = self.name_to_obj(lib_name)
+        if not y:
+            raise Utils.WafError('object %r was not found in uselib_local (required by %r)' % (lib_name, self.name))
+        y.post()
+        seen.add(lib_name)
+
+        # OPTIMIZATION 2: pre-compute ancestors shared libraries (100ms)
+        tmp.extend(y.shared_ancestors())
+
+        # link task and flags
+        if getattr(y, 'link_task', None):
+
+            link_name = y.target[y.target.rfind('/') + 1:]
+            if 'cstaticlib' in y.features:
+                app('STATICLIB', link_name)
+            elif 'cshlib' in y.features or 'cprogram' in y.features:
+                # WARNING some linkers can link against programs
+                app('LIB', link_name)
+
+            # the order
+            self.link_task.set_run_after(y.link_task)
+
+            # for the recompilation
+            dep_nodes = getattr(self.link_task, 'dep_nodes', [])
+            self.link_task.dep_nodes = dep_nodes + y.link_task.outputs
+
+            # OPTIMIZATION 3: reduce the amount of function calls
+            # add the link path too
+            par = y.link_task.outputs[0].parent
+            if id(par) not in seen_libpaths:
+                seen_libpaths.add(id(par))
+                tmp_path = par.bldpath(self.env)
+                if not tmp_path in env['LIBPATH']:
+                    env.prepend_value('LIBPATH', tmp_path)
+
+
+        # add ancestors uselib too - but only propagate those that have no staticlib
+        for v in self.to_list(y.uselib):
+            if v not in seen_uselib:
+                seen_uselib.add(v)
+                if not env['STATICLIB_' + v]:
+                    if not v in self.uselib:
+                        self.uselib.insert(0, v)
+
+    # 2. the case of the libs defined outside
+    for x in self.uselib:
+        for v in self.p_flag_vars:
+            val = self.env[v + '_' + x]
+            if val:
+                self.env.append_value(v, val)
+
+@feature('cprogram', 'cshlib', 'cstaticlib')
+@after('apply_lib_vars')
+@before('apply_obj_vars')
+def samba_before_apply_obj_vars(self):
+    """before apply_obj_vars for uselib, this removes the standard pathes"""
+
+    def is_standard_libpath(env, path):
+        for _path in env.STANDARD_LIBPATH:
+            if _path == os.path.normpath(path):
+                return True
+        return False
+
+    v = self.env
+
+    for i in v['RPATH']:
+        if is_standard_libpath(v, i):
+            v['RPATH'].remove(i)
+
+    for i in v['LIBPATH']:
+        if is_standard_libpath(v, i):
+            v['LIBPATH'].remove(i)
+
+@feature('cc')
+@before('apply_incpaths', 'apply_obj_vars_cc')
+def samba_stash_cppflags(self):
+    """Fix broken waf ordering of CPPFLAGS"""
+
+    self.env.SAVED_CPPFLAGS = self.env.CPPFLAGS
+    self.env.CPPFLAGS = []
+
+@feature('cc')
+@after('apply_incpaths', 'apply_obj_vars_cc')
+def samba_pop_cppflags(self):
+    """append stashed user CPPFLAGS after our internally computed flags"""
+
+    #
+    # Note that we don't restore the values to 'CPPFLAGS',
+    # but to _CCINCFLAGS instead.
+    #
+    # buildtools/wafadmin/Tools/cc.py defines the 'cc' task generator as
+    # '${CC} ${CCFLAGS} ${CPPFLAGS} ${_CCINCFLAGS} ${_CCDEFFLAGS} ${CC_SRC_F}${SRC} ${CC_TGT_F}${TGT}'
+    #
+    # Our goal is to effectively invert the order of ${CPPFLAGS} and
+    # ${_CCINCFLAGS}.
+    self.env.append_value('_CCINCFLAGS', self.env.SAVED_CPPFLAGS)
+    self.env.SAVED_CPPFLAGS = []
+
+@feature('cprogram', 'cshlib', 'cstaticlib')
+@before('apply_obj_vars', 'add_extra_flags')
+def samba_stash_linkflags(self):
+    """stash away LINKFLAGS in order to fix waf's broken ordering wrt or
+    user LDFLAGS"""
+
+    self.env.SAVE_LINKFLAGS = self.env.LINKFLAGS
+    self.env.LINKFLAGS = []
+
+@feature('cprogram', 'cshlib', 'cstaticlib')
+@after('apply_obj_vars', 'add_extra_flags')
+def samba_pop_linkflags(self):
+    """after apply_obj_vars append saved LDFLAGS"""
 
-# import cc
-# from TaskGen import extension
-# import Utils
-
-# @extension(cc.EXT_CC)
-# def c_hook(self, node):
-#     task = self.create_task('cc', node, node.change_ext('.o'))
-#     try:
-#         self.compiled_tasks.append(task)
-#     except AttributeError:
-#         raise Utils.WafError('Have you forgotten to set the feature "cc" on %s?' % str(self))
-
-#     bld = self.bld
-#     try:
-#         dc = bld.dc
-#     except AttributeError:
-#         dc = bld.dc = {}
-
-#     if task.outputs[0].id in dc:
-#         raise Utils.WafError('Samba, you are doing it wrong %r %s %s' % (task.outputs, task.generator, dc[task.outputs[0].id].generator))
-#     else:
-#         dc[task.outputs[0].id] = task
-
-#     return task
-
-
-def suncc_wrap(cls):
-    '''work around a problem with cc on solaris not handling module aliases
-    which have empty libs'''
-    if getattr(cls, 'solaris_wrap', False):
-        return
-    cls.solaris_wrap = True
-    oldrun = cls.run
-    def run(self):
-        if self.env.CC_NAME == "sun" and not self.inputs:
-            self.env = self.env.copy()
-            self.env.append_value('LINKFLAGS', '-')
-        return oldrun(self)
-    cls.run = run
-suncc_wrap(Task.TaskBase.classes['cc_link'])
+    self.env.append_value('LINKFLAGS', self.env.SAVE_LINKFLAGS)
+    self.env.SAVE_LINKFLAGS = []
index 1e2df90dac4760985d6fb15a23e5ce108c00d64b..b4427d3688471c28230aff36173c4aabd70cf4bf 100644 (file)
@@ -139,9 +139,7 @@ def write_build_options_footer(fp):
     fp.write("       output(screen, \"   sizeof(char):         %lu\\n\",(unsigned long)sizeof(char));\n")
     fp.write("       output(screen, \"   sizeof(int):          %lu\\n\",(unsigned long)sizeof(int));\n")
     fp.write("       output(screen, \"   sizeof(long):         %lu\\n\",(unsigned long)sizeof(long));\n")
-    fp.write("#if HAVE_LONGLONG\n")
     fp.write("       output(screen, \"   sizeof(long long):    %lu\\n\",(unsigned long)sizeof(long long));\n")
-    fp.write("#endif\n")
     fp.write("       output(screen, \"   sizeof(uint8):        %lu\\n\",(unsigned long)sizeof(uint8));\n")
     fp.write("       output(screen, \"   sizeof(uint16):       %lu\\n\",(unsigned long)sizeof(uint16));\n")
     fp.write("       output(screen, \"   sizeof(uint32):       %lu\\n\",(unsigned long)sizeof(uint32));\n")
@@ -207,6 +205,6 @@ def SAMBA_BLDOPTIONS(bld, target):
     '''generate the bld_options.c for Samba'''
     t = bld.SAMBA_GENERATOR(target,
                             rule=write_build_options,
-                            target=target,
-                            always=True)
+                            dep_vars=['defines'],
+                            target=target)
 Build.BuildContext.SAMBA_BLDOPTIONS = SAMBA_BLDOPTIONS
diff --git a/buildtools/wafsamba/samba_perl.py b/buildtools/wafsamba/samba_perl.py
new file mode 100644 (file)
index 0000000..3909aba
--- /dev/null
@@ -0,0 +1,62 @@
+import Build
+from samba_utils import *
+from Configure import conf
+
+done = {}
+
+@conf
+def SAMBA_CHECK_PERL(conf, mandatory=True, version=(5,0,0)):
+    #
+    # TODO: use the @runonce mechanism for this.
+    # The problem is that @runonce currently does
+    # not seem to work together with @conf...
+    # So @runonce (and/or) @conf needs fixing.
+    #
+    if "done" in done:
+        return
+    done["done"] = True
+    conf.find_program('perl', var='PERL', mandatory=mandatory)
+    conf.check_tool('perl')
+    path_perl = conf.find_program('perl')
+    conf.env.PERL_SPECIFIED = (conf.env.PERL != path_perl)
+    conf.check_perl_version(version)
+
+    def read_perl_config_var(cmd):
+        return Utils.to_list(Utils.cmd_output([conf.env.PERL, '-MConfig', '-e', cmd]))
+
+    def check_perl_config_var(var):
+        conf.start_msg("Checking for perl $Config{%s}:" % var)
+        try:
+            v = read_perl_config_var('print $Config{%s}' % var)[0]
+            conf.end_msg("'%s'" % (v), 'GREEN')
+            return v
+        except IndexError:
+            conf.end_msg(False, 'YELLOW')
+            pass
+        return None
+
+    vendor_prefix = check_perl_config_var('vendorprefix')
+
+    perl_arch_install_dir = None
+    if vendor_prefix == conf.env.PREFIX:
+        perl_arch_install_dir = check_perl_config_var('vendorarch');
+    if perl_arch_install_dir is None:
+        perl_arch_install_dir = "${LIBDIR}/perl5";
+    conf.start_msg("PERL_ARCH_INSTALL_DIR: ")
+    conf.end_msg("'%s'" % (perl_arch_install_dir), 'GREEN')
+    conf.env.PERL_ARCH_INSTALL_DIR = perl_arch_install_dir
+
+    perl_lib_install_dir = None
+    if vendor_prefix == conf.env.PREFIX:
+        perl_lib_install_dir = check_perl_config_var('vendorlib');
+    if perl_lib_install_dir is None:
+        perl_lib_install_dir = "${DATADIR}/perl5";
+    conf.start_msg("PERL_LIB_INSTALL_DIR: ")
+    conf.end_msg("'%s'" % (perl_lib_install_dir), 'GREEN')
+    conf.env.PERL_LIB_INSTALL_DIR = perl_lib_install_dir
+
+    perl_inc = read_perl_config_var('print "@INC"')
+    perl_inc.remove('.')
+    conf.start_msg("PERL_INC: ")
+    conf.end_msg("%s" % (perl_inc), 'GREEN')
+    conf.env.PERL_INC = perl_inc
diff --git a/buildtools/wafsamba/samba_third_party.py b/buildtools/wafsamba/samba_third_party.py
new file mode 100644 (file)
index 0000000..46a1b94
--- /dev/null
@@ -0,0 +1,35 @@
+# functions to support third party libraries
+
+from Configure import conf
+import sys, Logs, os
+from samba_bundled import *
+
+@conf
+def CHECK_FOR_THIRD_PARTY(conf):
+    return os.path.exists(os.path.join(Utils.g_module.srcdir, 'third_party'))
+
+Build.BuildContext.CHECK_FOR_THIRD_PARTY = CHECK_FOR_THIRD_PARTY
+
+@conf
+def CHECK_ZLIB(conf):
+    version_check='''
+    #if (ZLIB_VERNUM >= 0x1230)
+    #else
+    #error "ZLIB_VERNUM < 0x1230"
+    #endif
+    z_stream *z;
+    inflateInit2(z, -15);
+    '''
+    return conf.CHECK_BUNDLED_SYSTEM('z', minversion='1.2.3', pkg='zlib',
+                                     checkfunctions='zlibVersion',
+                                     headers='zlib.h',
+                                     checkcode=version_check,
+                                     implied_deps='replace')
+
+Build.BuildContext.CHECK_ZLIB = CHECK_ZLIB
+
+@conf
+def CHECK_POPT(conf):
+    return conf.CHECK_BUNDLED_SYSTEM('popt', checkfunctions='poptGetContext', headers='popt.h')
+
+Build.BuildContext.CHECK_POPT = CHECK_POPT
index 0b0bb483781ae5341c6574b4da80b3be111dc383..df4a552dbeed5b3408444db9b49b7d73389ac61b 100644 (file)
@@ -39,8 +39,8 @@ def GET_TARGET_TYPE(ctx, target):
 # this is used as a decorator to make functions only
 # run once. Based on the idea from
 # http://stackoverflow.com/questions/815110/is-there-a-decorator-to-simply-cache-function-return-values
-runonce_ret = {}
 def runonce(function):
+    runonce_ret = {}
     def runonce_wrapper(*args):
         if args in runonce_ret:
             return runonce_ret[args]
@@ -214,7 +214,8 @@ def TO_LIST(str, delimiter=None):
     if str is None:
         return []
     if isinstance(str, list):
-        return str
+        # we need to return a new independent list...
+        return list(str)
     if len(str) == 0:
         return []
     lst = str.split(delimiter)
diff --git a/buildtools/wafsamba/test_duplicate_symbol.sh b/buildtools/wafsamba/test_duplicate_symbol.sh
new file mode 100755 (executable)
index 0000000..89a4027
--- /dev/null
@@ -0,0 +1,12 @@
+#!/bin/sh
+# Run the waf duplicate symbol check, wrapped in subunit.
+
+. testprogs/blackbox/subunit.sh
+
+subunit_start_test duplicate_symbols
+
+if ./buildtools/bin/waf build --dup-symbol-check; then
+       subunit_pass_test duplicate_symbols
+else
+       echo | subunit_fail_test duplicate_symbols
+fi
index 8ec4cb808632eaa97e75ba7a2ab2f4902e5d14e5..c05431568ab41fa23b2f1a2fea8f83f2ebec63b4 100644 (file)
@@ -16,8 +16,10 @@ from samba_patterns import *
 from samba_pidl import *
 from samba_autoproto import *
 from samba_python import *
+from samba_perl import *
 from samba_deps import *
 from samba_bundled import *
+from samba_third_party import *
 import samba_install
 import samba_conftests
 import samba_abi
@@ -92,6 +94,11 @@ def ADD_INIT_FUNCTION(bld, subsystem, target, init_function):
 Build.BuildContext.ADD_INIT_FUNCTION = ADD_INIT_FUNCTION
 
 
+def generate_empty_file(task):
+    target_fname = installed_location=task.outputs[0].bldpath(task.env)
+    target_file = open(installed_location, 'w')
+    target_file.close()
+    return 0
 
 #################################################################
 def SAMBA_LIBRARY(bld, libname, source,
@@ -108,6 +115,7 @@ def SAMBA_LIBRARY(bld, libname, source,
                   ldflags='',
                   external_library=False,
                   realname=None,
+                  keep_underscore=False,
                   autoproto=None,
                   autoproto_extra_source='',
                   group='main',
@@ -121,7 +129,8 @@ def SAMBA_LIBRARY(bld, libname, source,
                   pyembed=False,
                   pyext=False,
                   target_type='LIBRARY',
-                  bundled_extension=True,
+                  bundled_extension=False,
+                  bundled_name=None,
                   link_name=None,
                   abi_directory=None,
                   abi_match=None,
@@ -130,7 +139,7 @@ def SAMBA_LIBRARY(bld, libname, source,
                   private_library=False,
                   grouping_library=False,
                   allow_undefined_symbols=False,
-                  allow_warnings=True,
+                  allow_warnings=False,
                   enabled=True):
     '''define a Samba library'''
 
@@ -146,9 +155,15 @@ def SAMBA_LIBRARY(bld, libname, source,
         source = bld.SUBDIR(subdir, source)
 
     # remember empty libraries, so we can strip the dependencies
-    if ((source == '') or (source == [])) and deps == '' and public_deps == '':
-        SET_TARGET_TYPE(bld, libname, 'EMPTY')
-        return
+    if ((source == '') or (source == [])):
+        if deps == '' and public_deps == '':
+            SET_TARGET_TYPE(bld, libname, 'EMPTY')
+            return
+        empty_c = libname + '.empty.c'
+        bld.SAMBA_GENERATOR('%s_empty_c' % libname,
+                            rule=generate_empty_file,
+                            target=empty_c)
+        source=empty_c
 
     if BUILTIN_LIBRARY(bld, libname):
         obj_target = libname
@@ -209,11 +224,19 @@ def SAMBA_LIBRARY(bld, libname, source,
             raise Utils.WafError("public library '%s' must have header files" %
                        libname)
 
-    if target_type == 'PYTHON' or realname or not private_library:
-        bundled_name = libname.replace('_', '-')
+    if bundled_name is not None:
+        pass
+    elif target_type == 'PYTHON' or realname or not private_library:
+        if keep_underscore:
+            bundled_name = libname
+        else:
+            bundled_name = libname.replace('_', '-')
     else:
-        bundled_name = PRIVATE_NAME(bld, libname, bundled_extension,
-            private_library)
+        assert (private_library == True and realname is None)
+        if abi_directory or vnum or soname:
+            bundled_extension=True
+        bundled_name = PRIVATE_NAME(bld, libname.replace('_', '-'),
+                                    bundled_extension, private_library)
 
     ldflags = TO_LIST(ldflags)
 
@@ -347,10 +370,10 @@ def SAMBA_BINARY(bld, binname, source,
     # only specify PIE flags for binaries
     pie_cflags = cflags
     pie_ldflags = TO_LIST(ldflags)
-    if bld.env['ENABLE_PIE'] == True:
+    if bld.env['ENABLE_PIE'] is True:
         pie_cflags += ' -fPIE'
         pie_ldflags.extend(TO_LIST('-pie'))
-    if bld.env['ENABLE_RELRO'] == True:
+    if bld.env['ENABLE_RELRO'] is True:
         pie_ldflags.extend(TO_LIST('-Wl,-z,relro,-z,now'))
 
     # first create a target for building the object files for this binary
@@ -418,17 +441,19 @@ def SAMBA_MODULE(bld, modname, source,
                  pyembed=False,
                  manpages=None,
                  allow_undefined_symbols=False,
-                 allow_warnings=True
+                 allow_warnings=False
                  ):
     '''define a Samba module.'''
 
+    bld.ASSERT(subsystem, "You must specify a subsystem for SAMBA_MODULE(%s)" % modname)
+
     source = bld.EXPAND_VARIABLES(source, vars=vars)
     if subdir:
         source = bld.SUBDIR(subdir, source)
 
     if internal_module or BUILTIN_LIBRARY(bld, modname):
         # Do not create modules for disabled subsystems
-        if subsystem and GET_TARGET_TYPE(bld, subsystem) == 'DISABLED':
+        if GET_TARGET_TYPE(bld, subsystem) == 'DISABLED':
             return
         bld.SAMBA_SUBSYSTEM(modname, source,
                     deps=deps,
@@ -449,18 +474,17 @@ def SAMBA_MODULE(bld, modname, source,
         return
 
     # Do not create modules for disabled subsystems
-    if subsystem and GET_TARGET_TYPE(bld, subsystem) == 'DISABLED':
+    if GET_TARGET_TYPE(bld, subsystem) == 'DISABLED':
         return
 
-    obj_target = modname + '.objlist'
-
     realname = modname
-    if subsystem is not None:
-        deps += ' ' + subsystem
-        while realname.startswith("lib"+subsystem+"_"):
-            realname = realname[len("lib"+subsystem+"_"):]
-        while realname.startswith(subsystem+"_"):
-            realname = realname[len(subsystem+"_"):]
+    deps += ' ' + subsystem
+    while realname.startswith("lib"+subsystem+"_"):
+        realname = realname[len("lib"+subsystem+"_"):]
+    while realname.startswith(subsystem+"_"):
+        realname = realname[len(subsystem+"_"):]
+
+    build_name = "%s_module_%s" % (subsystem, realname)
 
     realname = bld.make_libname(realname)
     while realname.startswith("lib"):
@@ -481,6 +505,7 @@ def SAMBA_MODULE(bld, modname, source,
                       local_include=local_include,
                       global_include=global_include,
                       vars=vars,
+                      bundled_name=build_name,
                       link_name=build_link_name,
                       install_path="${MODULESDIR}/%s" % subsystem,
                       pyembed=pyembed,
@@ -518,7 +543,7 @@ def SAMBA_SUBSYSTEM(bld, modname, source,
                     vars=None,
                     subdir=None,
                     hide_symbols=False,
-                    allow_warnings=True,
+                    allow_warnings=False,
                     pyext=False,
                     pyembed=False):
     '''define a Samba subsystem'''
@@ -528,9 +553,15 @@ def SAMBA_SUBSYSTEM(bld, modname, source,
         return
 
     # remember empty subsystems, so we can strip the dependencies
-    if ((source == '') or (source == [])) and deps == '' and public_deps == '':
-        SET_TARGET_TYPE(bld, modname, 'EMPTY')
-        return
+    if ((source == '') or (source == [])):
+        if deps == '' and public_deps == '':
+            SET_TARGET_TYPE(bld, modname, 'EMPTY')
+            return
+        empty_c = modname + '.empty.c'
+        bld.SAMBA_GENERATOR('%s_empty_c' % modname,
+                            rule=generate_empty_file,
+                            target=empty_c)
+        source=empty_c
 
     if not SET_TARGET_TYPE(bld, modname, 'SUBSYSTEM'):
         return
@@ -588,6 +619,7 @@ def SAMBA_GENERATOR(bld, name, rule, source='', target='',
                     public_headers_install=True,
                     header_path=None,
                     vars=None,
+                    dep_vars=[],
                     always=False):
     '''A generic source generator target'''
 
@@ -597,11 +629,8 @@ def SAMBA_GENERATOR(bld, name, rule, source='', target='',
     if not enabled:
         return
 
-    dep_vars = []
-    if isinstance(vars, dict):
-        dep_vars = vars.keys()
-    elif isinstance(vars, list):
-        dep_vars = vars
+    dep_vars.append('ruledeps')
+    dep_vars.append('SAMBA_GENERATOR_VARS')
 
     bld.SET_BUILD_GROUP(group)
     t = bld(
@@ -613,9 +642,13 @@ def SAMBA_GENERATOR(bld, name, rule, source='', target='',
         before='cc',
         ext_out='.c',
         samba_type='GENERATOR',
-        dep_vars = [rule] + dep_vars,
+        dep_vars = dep_vars,
         name=name)
 
+    if vars is None:
+        vars = {}
+    t.env.SAMBA_GENERATOR_VARS = vars
+
     if always:
         t.always = True
 
@@ -711,8 +744,6 @@ def copy_and_fix_python_path(task):
         replacement="""sys.path.insert(0, "%s")
 sys.path.insert(1, "%s")""" % (task.env["PYTHONARCHDIR"], task.env["PYTHONDIR"])
 
-    shebang = None
-
     if task.env["PYTHON"][0] == "/":
         replacement_shebang = "#!%s\n" % task.env["PYTHON"]
     else:
@@ -724,7 +755,36 @@ sys.path.insert(1, "%s")""" % (task.env["PYTHONARCHDIR"], task.env["PYTHONDIR"])
     lineno = 0
     for line in source_file:
         newline = line
-        if lineno == 0 and task.env["PYTHON_SPECIFIED"] == True and line[:2] == "#!":
+        if (lineno == 0 and task.env["PYTHON_SPECIFIED"] is True and
+                line[:2] == "#!"):
+            newline = replacement_shebang
+        elif pattern in line:
+            newline = line.replace(pattern, replacement)
+        installed_file.write(newline)
+        lineno = lineno + 1
+    installed_file.close()
+    os.chmod(installed_location, 0755)
+    return 0
+
+def copy_and_fix_perl_path(task):
+    pattern='use lib "$RealBin/lib";'
+
+    replacement = ""
+    if not task.env["PERL_LIB_INSTALL_DIR"] in task.env["PERL_INC"]:
+         replacement = 'use lib "%s";' % task.env["PERL_LIB_INSTALL_DIR"]
+
+    if task.env["PERL"][0] == "/":
+        replacement_shebang = "#!%s\n" % task.env["PERL"]
+    else:
+        replacement_shebang = "#!/usr/bin/env %s\n" % task.env["PERL"]
+
+    installed_location=task.outputs[0].bldpath(task.env)
+    source_file = open(task.inputs[0].srcpath(task.env))
+    installed_file = open(installed_location, 'w')
+    lineno = 0
+    for line in source_file:
+        newline = line
+        if lineno == 0 and task.env["PERL_SPECIFIED"] == True and line[:2] == "#!":
             newline = replacement_shebang
         elif pattern in line:
             newline = line.replace(pattern, replacement)
@@ -736,7 +796,8 @@ sys.path.insert(1, "%s")""" % (task.env["PYTHONARCHDIR"], task.env["PYTHONDIR"])
 
 
 def install_file(bld, destdir, file, chmod=MODE_644, flat=False,
-                 python_fixup=False, destname=None, base_name=None):
+                 python_fixup=False, perl_fixup=False,
+                 destname=None, base_name=None):
     '''install a file'''
     destdir = bld.EXPAND_VARIABLES(destdir)
     if not destname:
@@ -745,16 +806,22 @@ def install_file(bld, destdir, file, chmod=MODE_644, flat=False,
             destname = os.path.basename(destname)
     dest = os.path.join(destdir, destname)
     if python_fixup:
-        # fixup the python path it will use to find Samba modules
+        # fix the path python will use to find Samba modules
         inst_file = file + '.inst'
         bld.SAMBA_GENERATOR('python_%s' % destname,
                             rule=copy_and_fix_python_path,
+                            dep_vars=["PYTHON","PYTHON_SPECIFIED","PYTHONDIR","PYTHONARCHDIR"],
+                            source=file,
+                            target=inst_file)
+        file = inst_file
+    if perl_fixup:
+        # fix the path perl will use to find Samba modules
+        inst_file = file + '.inst'
+        bld.SAMBA_GENERATOR('perl_%s' % destname,
+                            rule=copy_and_fix_perl_path,
+                            dep_vars=["PERL","PERL_SPECIFIED","PERL_LIB_INSTALL_DIR"],
                             source=file,
                             target=inst_file)
-        bld.add_manual_dependency(bld.path.find_or_declare(inst_file), bld.env["PYTHONARCHDIR"])
-        bld.add_manual_dependency(bld.path.find_or_declare(inst_file), bld.env["PYTHONDIR"])
-        bld.add_manual_dependency(bld.path.find_or_declare(inst_file), str(bld.env["PYTHON_SPECIFIED"]))
-        bld.add_manual_dependency(bld.path.find_or_declare(inst_file), bld.env["PYTHON"])
         file = inst_file
     if base_name:
         file = os.path.join(base_name, file)
@@ -762,12 +829,13 @@ def install_file(bld, destdir, file, chmod=MODE_644, flat=False,
 
 
 def INSTALL_FILES(bld, destdir, files, chmod=MODE_644, flat=False,
-                  python_fixup=False, destname=None, base_name=None):
+                  python_fixup=False, perl_fixup=False,
+                  destname=None, base_name=None):
     '''install a set of files'''
     for f in TO_LIST(files):
         install_file(bld, destdir, f, chmod=chmod, flat=flat,
-                     python_fixup=python_fixup, destname=destname,
-                     base_name=base_name)
+                     python_fixup=python_fixup, perl_fixup=perl_fixup,
+                     destname=destname, base_name=base_name)
 Build.BuildContext.INSTALL_FILES = INSTALL_FILES
 
 
index 1a2cfe661f8e847ee301244e16f8f4ae6f48ccbd..8027c00dd213eea76f3a6660e14770ba204620bf 100755 (executable)
@@ -117,6 +117,9 @@ def set_options(opt):
     gr.add_option('--git-local-changes',
                   help=("mark version with + if local git changes"),
                   action='store_true', dest='GIT_LOCAL_CHANGES', default=False)
+    gr.add_option('--address-sanitizer',
+                   help=("Enable address sanitizer compile and linker flags"),
+                   action="store_true", dest='address_sanitizer', default=False)
 
     gr.add_option('--abi-check',
                   help=("Check ABI signatures for libraries"),
@@ -211,6 +214,8 @@ def configure(conf):
 
     conf.check_tool('compiler_cc')
 
+    conf.CHECK_STANDARD_LIBPATH()
+
     # we need git for 'waf dist'
     conf.find_program('git', var='GIT')
 
@@ -295,6 +300,23 @@ def configure(conf):
                     headers='stdio.h',
                     msg='Checking simple C program')
 
+    # Try to find the right extra flags for -Werror behaviour
+    for f in ["-Werror",       # GCC
+              "-errwarn=%all", # Sun Studio
+              "-qhalt=w",     # IBM xlc
+              "-w2",           # Tru64
+             ]:
+        if conf.CHECK_CFLAGS([f], '''
+'''):
+            if not 'WERROR_CFLAGS' in conf.env:
+                conf.env['WERROR_CFLAGS'] = []
+            conf.env['WERROR_CFLAGS'].extend([f])
+            break
+
+    # check which compiler/linker flags are needed for rpath support
+    if not conf.CHECK_LDFLAGS(['-Wl,-rpath,.']) and conf.CHECK_LDFLAGS(['-Wl,-R,.']):
+        conf.env['RPATH_ST'] = '-Wl,-R,%s'
+
     # check for rpath
     if conf.CHECK_LIBRARY_SUPPORT(rpath=True):
         support_rpath = True
@@ -324,6 +346,13 @@ def configure(conf):
     else:
         conf.env.HAVE_LD_VERSION_SCRIPT = False
 
+    if conf.CHECK_CFLAGS(['-fvisibility=hidden'] + conf.env.WERROR_CFLAGS):
+        conf.env.VISIBILITY_CFLAGS = '-fvisibility=hidden'
+        conf.CHECK_CODE('''int main(void) { return 0; }
+                           __attribute__((visibility("default"))) void vis_foo2(void) {}''',
+                        cflags=conf.env.VISIBILITY_CFLAGS,
+                        define='HAVE_VISIBILITY_ATTR', addmain=False)
+
     if sys.platform.startswith('aix'):
         conf.DEFINE('_ALL_SOURCE', 1, add_to_cflags=True)
         # Might not be needed if ALL_SOURCE is defined
@@ -359,6 +388,27 @@ def configure(conf):
     conf.DEFINE('_GNU_SOURCE', 1, add_to_cflags=True)
     conf.DEFINE('_XOPEN_SOURCE_EXTENDED', 1, add_to_cflags=True)
 
+    # on Tru64 certain features are only available with _OSF_SOURCE set to 1
+    # and _XOPEN_SOURCE set to 600
+    if conf.env['SYSTEM_UNAME_SYSNAME'] == 'OSF1':
+        conf.DEFINE('_OSF_SOURCE', 1, add_to_cflags=True)
+        conf.DEFINE('_XOPEN_SOURCE', 600, add_to_cflags=True)
+
+    # SCM_RIGHTS is only avail if _XOPEN_SOURCE iŃ• defined on IRIX
+    if conf.env['SYSTEM_UNAME_SYSNAME'] == 'IRIX':
+        conf.DEFINE('_XOPEN_SOURCE', 600, add_to_cflags=True)
+        conf.DEFINE('_BSD_TYPES', 1, add_to_cflags=True)
+
+    # Try to find the right extra flags for C99 initialisers
+    for f in ["", "-AC99", "-qlanglvl=extc99", "-qlanglvl=stdc99", "-c99"]:
+        if conf.CHECK_CFLAGS([f], '''
+struct foo {int x;char y;};
+struct foo bar = { .y = 'X', .x = 1 };
+'''):
+            if f != "":
+                conf.ADD_CFLAGS(f)
+            break
+
     # get the base headers we'll use for the rest of the tests
     conf.CHECK_HEADERS('stdio.h sys/types.h sys/stat.h stdlib.h stddef.h memory.h string.h',
                        add_headers=True)
index f940898e4b9b796781e889b6e85c085edea67091..3ff4e365771d81c8a624837e939614398e5357fe 100644 (file)
 #include <stdarg.h>
 #include <errno.h>
 
+#ifndef HAVE_DECL_EWOULDBLOCK
+#define EWOULDBLOCK EAGAIN
+#endif
+
 #if defined(_MSC_VER) || defined(__MINGW32__)
 #include "win32_replace.h"
 #endif
@@ -904,4 +908,9 @@ bool nss_wrapper_hosts_enabled(void);
 bool socket_wrapper_enabled(void);
 bool uid_wrapper_enabled(void);
 
+/* Needed for Solaris atomic_add_XX functions. */
+#if defined(HAVE_SYS_ATOMIC_H)
+#include <sys/atomic.h>
+#endif
+
 #endif /* _LIBREPLACE_REPLACE_H */
index 6b4a711045c4c4a5530b3c22f2f5894a48242991..86ba74cf4f8dc9101ba9d41005f12d9abc4c4642 100644 (file)
@@ -445,6 +445,10 @@ static int dopr(char *buffer, size_t maxlen, const char *format, va_list args_in
                                        ch = *format++;
                                }
                                break;
+                       case 'j':
+                               cnk->cflags = DP_C_LLONG;
+                               ch = *format++;
+                               break;
                        case 'L':
                                cnk->cflags = DP_C_LDOUBLE;
                                ch = *format++;
index b234f101efced6e081c99c870992b85dd89cabbf..bd6e6a0dd19887b2e08eb9b7b677228c91e4c95e 100644 (file)
 
 */
 
+#ifdef HAVE_UNISTD_H
 #include <unistd.h>
+#endif
+
 #include <sys/stat.h>
 
 #ifdef HAVE_SYS_PARAM_H
index 273cb716cf4b339be5fd0d7932389b3f855e582c..4a3fd07d8e1e0a42c956a11f3c1b35c3a2043dcf 100644 (file)
@@ -31,7 +31,9 @@
 #error "AC_LIBREPLACE_NETWORK_CHECKS missing in configure"
 #endif
 
+#ifdef HAVE_UNISTD_H
 #include <unistd.h>
+#endif
 
 #ifdef HAVE_SYS_SOCKET_H
 #include <sys/socket.h>
 #include <net/if.h>
 #endif
 
-#ifdef HAVE_UNISTD_H
-#include <unistd.h>
-#endif
-
 #ifdef HAVE_SYS_IOCTL_H
 #include <sys/ioctl.h>
 #endif
index f8b9a774b3ddb0acbdde4fc80779135ebb5372d8..ecc9f603d96a0800ca1cc751afb09201fd972b63 100644 (file)
 
 */
 
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+
 #ifdef HAVE_PWD_H
 #include <pwd.h>
 #endif
index 11c5390d90138ad0106af2feab6e56713cb71497..9e945c3ccfa02b0c272d5994b5d3cf9a36c36483 100644 (file)
 #include <sys/epoll.h>
 #endif
 
+#ifdef HAVE_SOLARIS_PORTS
+#include <port.h>
+#endif
+
 #ifndef SELECT_CAST
 #define SELECT_CAST
 #endif
diff --git a/lib/replace/system/threads.h b/lib/replace/system/threads.h
new file mode 100644 (file)
index 0000000..25d3502
--- /dev/null
@@ -0,0 +1,48 @@
+#ifndef _system_threads_h
+#define _system_threads_h
+/*
+   Unix SMB/CIFS implementation.
+
+   macros to go along with the lib/replace/ portability layer code
+
+   Copyright (C) Volker Lendecke 2012
+
+     ** NOTE! The following LGPL license applies to the replace
+     ** library. This does NOT imply that all of Samba is released
+     ** under the LGPL
+
+   This library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 3 of the License, or (at your option) any later version.
+
+   This library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with this library; if not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include <pthread.h>
+
+#if defined(HAVE_PTHREAD_MUTEXATTR_SETROBUST_NP) && \
+       !defined(HAVE_PTHREAD_MUTEXATTR_SETROBUST)
+
+#define pthread_mutexattr_setrobust pthread_mutexattr_setrobust_np
+
+/*
+ * We assume that PTHREAD_MUTEX_ROBUST_NP goes along with
+ * pthread_mutexattr_setrobust_np()
+ */
+#define PTHREAD_MUTEX_ROBUST PTHREAD_MUTEX_ROBUST_NP
+
+#endif
+
+#if defined(HAVE_PTHREAD_MUTEX_CONSISTENT_NP) && \
+       !defined(HAVE_PTHREAD_MUTEX_CONSISTENT)
+#define pthread_mutex_consistent pthread_mutex_consistent_np
+#endif
+
+#endif
index a11ed3b370bfefddda6532bac837da861645fcf8..9e2115bb8115317ad1be4619640c64daa98b2f17 100644 (file)
@@ -22,7 +22,7 @@
 
 static int test_readdir_os2_delete_ret;
 
-#define FAILED(d) (printf("failure: readdir [\nFailed for %s - %d = %s\n]\n", d, errno, strerror(errno)), test_readdir_os2_delete_ret = 1, 1)
+#define FAILED(d) (printf("failure: readdir [\nFailed for %s - %d = %s\n]\n", d, errno, strerror(errno)), test_readdir_os2_delete_ret = 1)
 
 #ifndef MIN
 #define MIN(a,b) ((a)<(b)?(a):(b))
index fd5b386e4e37c2dea39bc05ddca97a1005df7021..f8a017920df515b82dd1abad9ed989f6042acf6e 100644 (file)
@@ -5,16 +5,16 @@ VERSION = '1.2.1'
 
 blddir = 'bin'
 
-import sys, os, Utils
+import sys, os
 
 # find the buildtools directory
 srcdir = '.'
 while not os.path.exists(srcdir+'/buildtools') and len(srcdir.split('/')) < 5:
-    srcdir = '../' + srcdir
+    srcdir = srcdir + '/..'
 sys.path.insert(0, srcdir + '/buildtools/wafsamba')
 
 import wafsamba, samba_dist
-import Options, os, preproc
+import Options
 
 samba_dist.DIST_DIRS('lib/replace buildtools:buildtools')
 
@@ -32,50 +32,13 @@ def configure(conf):
     conf.DEFINE('HAVE_LIBREPLACE', 1)
     conf.DEFINE('LIBREPLACE_NETWORK_CHECKS', 1)
 
-    # on Tru64 certain features are only available with _OSF_SOURCE set to 1
-    # and _XOPEN_SOURCE set to 600
-    if conf.env['SYSTEM_UNAME_SYSNAME'] == 'OSF1':
-        conf.DEFINE('_OSF_SOURCE', 1, add_to_cflags=True)
-        conf.DEFINE('_XOPEN_SOURCE', 600, add_to_cflags=True)
-
-    # SCM_RIGHTS is only avail if _XOPEN_SOURCE iŃ• defined on IRIX
-    if conf.env['SYSTEM_UNAME_SYSNAME'] == 'IRIX':
-        conf.DEFINE('_XOPEN_SOURCE', 600, add_to_cflags=True)
-        conf.DEFINE('_BSD_TYPES', 1, add_to_cflags=True)
-
-    # Try to find the right extra flags for C99 initialisers
-    for f in ["", "-AC99", "-qlanglvl=extc99", "-qlanglvl=stdc99", "-c99"]:
-        if conf.CHECK_CFLAGS([f], '''
-struct foo {int x;char y;};
-struct foo bar = { .y = 'X', .x = 1 };
-'''):
-            if f != "":
-                conf.ADD_CFLAGS(f)
-            break
-
-    if conf.CHECK_CFLAGS(['-fstack-protector']) and conf.CHECK_LDFLAGS(['-fstack-protector']):
-        conf.ADD_CFLAGS('-fstack-protector')
-        conf.ADD_LDFLAGS('-fstack-protector')
-
-    # Try to find the right extra flags for -Werror behaviour
-    for f in ["-Werror",       # GCC
-             "-errwarn=%all", # Sun Studio
-             "-qhalt=w",     # IBM xlc
-             "-w2",           # Tru64
-             ]:
-        if conf.CHECK_CFLAGS([f], '''
-'''):
-            if not 'WERROR_CFLAGS' in conf.env:
-                conf.env['WERROR_CFLAGS'] = []
-            conf.env['WERROR_CFLAGS'].extend([f])
-            break
-
     conf.CHECK_HEADERS('linux/types.h crypt.h locale.h acl/libacl.h compat.h')
     conf.CHECK_HEADERS('acl/libacl.h attr/xattr.h compat.h ctype.h dustat.h')
     conf.CHECK_HEADERS('fcntl.h fnmatch.h glob.h history.h krb5.h langinfo.h')
     conf.CHECK_HEADERS('libaio.h locale.h ndir.h pwd.h')
     conf.CHECK_HEADERS('shadow.h sys/acl.h')
     conf.CHECK_HEADERS('sys/attributes.h attr/attributes.h sys/capability.h sys/dir.h sys/epoll.h')
+    conf.CHECK_HEADERS('port.h')
     conf.CHECK_HEADERS('sys/fcntl.h sys/filio.h sys/filsys.h sys/fs/s5param.h sys/fs/vx/quota.h')
     conf.CHECK_HEADERS('sys/id.h sys/ioctl.h sys/ipc.h sys/mman.h sys/mode.h sys/ndir.h sys/priv.h')
     conf.CHECK_HEADERS('sys/resource.h sys/security.h sys/shm.h sys/statfs.h sys/statvfs.h sys/termio.h')
@@ -110,6 +73,7 @@ struct foo bar = { .y = 'X', .x = 1 };
     conf.CHECK_HEADERS('sys/extattr.h sys/ea.h sys/proplist.h sys/cdefs.h')
     conf.CHECK_HEADERS('utmp.h utmpx.h lastlog.h malloc.h')
     conf.CHECK_HEADERS('syscall.h sys/syscall.h inttypes.h')
+    conf.CHECK_HEADERS('sys/atomic.h')
 
     # Check for process set name support
     conf.CHECK_CODE('''
@@ -229,6 +193,30 @@ struct foo bar = { .y = 'X', .x = 1 };
                        msg="Checking whether we have ucontext_t",
                        headers='signal.h sys/ucontext.h')
 
+    # Check for atomic builtins. */
+    conf.CHECK_CODE('''
+                    int main(void) {
+                        int i;
+                        (void)__sync_fetch_and_add(&i, 1);
+                        return 0;
+                    }
+                    ''',
+                    'HAVE___SYNC_FETCH_AND_ADD',
+                    msg='Checking for __sync_fetch_and_add compiler builtin')
+
+    conf.CHECK_CODE('''
+                    #include <stdint.h>
+                    #include <sys/atomic.h>
+                    int main(void) {
+                        int32_t i;
+                        atomic_add_32(&i, 1);
+                        return 0;
+                    }
+                    ''',
+                    'HAVE_ATOMIC_ADD_32',
+                    headers='stdint.h sys/atomic.h',
+                    msg='Checking for atomic_add_32 compiler builtin')
+
     # these may be builtins, so we need the link=False strategy
     conf.CHECK_FUNCS('strdup memmem printf memset memcpy memmove strcpy strncpy bzero', link=False)
 
@@ -263,8 +251,8 @@ struct foo bar = { .y = 'X', .x = 1 };
                 checklibc=True)
     if not conf.CHECK_FUNCS('getpeereid'):
         conf.CHECK_FUNCS_IN('getpeereid', 'bsd', headers='sys/types.h bsd/unistd.h')
-    if not conf.CHECK_FUNCS_IN('setproctitle', 'bsd', headers='sys/types.h bsd/unistd.h'):
-        conf.CHECK_FUNCS_IN('setproctitle', 'setproctitle', headers='setproctitle.h')
+    if not conf.CHECK_FUNCS_IN('setproctitle', 'setproctitle', headers='setproctitle.h'):
+        conf.CHECK_FUNCS_IN('setproctitle', 'bsd', headers='sys/types.h bsd/unistd.h')
 
     conf.CHECK_CODE('''
                 struct ucred cred;
@@ -296,6 +284,7 @@ struct foo bar = { .y = 'X', .x = 1 };
     conf.CHECK_FUNCS('timegm getifaddrs freeifaddrs mmap setgroups syscall setsid')
     conf.CHECK_FUNCS('getgrent_r getgrgid_r getgrnam_r getgrouplist getpagesize')
     conf.CHECK_FUNCS('getpwent_r getpwnam_r getpwuid_r epoll_create')
+    conf.CHECK_FUNCS('port_create')
 
     conf.SET_TARGET_TYPE('attr', 'EMPTY')
 
@@ -422,6 +411,69 @@ removeea setea
 
     conf.CHECK_FUNCS_IN('pthread_create', 'pthread', checklibc=True, headers='pthread.h')
 
+    PTHREAD_CFLAGS='error'
+    PTHREAD_LDFLAGS='error'
+
+    if PTHREAD_LDFLAGS == 'error':
+        if conf.CHECK_FUNCS_IN('pthread_attr_init', 'pthread'):
+            PTHREAD_CFLAGS='-D_REENTRANT -D_POSIX_PTHREAD_SEMANTICS'
+            PTHREAD_LDFLAGS='-lpthread'
+    if PTHREAD_LDFLAGS == 'error':
+        if conf.CHECK_FUNCS_IN('pthread_attr_init', 'pthreads'):
+            PTHREAD_CFLAGS='-D_THREAD_SAFE'
+            PTHREAD_LDFLAGS='-lpthreads'
+    if PTHREAD_LDFLAGS == 'error':
+        if conf.CHECK_FUNCS_IN('pthread_attr_init', 'c_r'):
+            PTHREAD_CFLAGS='-D_THREAD_SAFE -pthread'
+            PTHREAD_LDFLAGS='-pthread'
+    if PTHREAD_LDFLAGS == 'error':
+        if conf.CHECK_FUNCS('pthread_attr_init'):
+            PTHREAD_CFLAGS='-D_REENTRANT'
+            PTHREAD_LDFLAGS='-lpthread'
+    # especially for HP-UX, where the CHECK_FUNC macro fails to test for
+    # pthread_attr_init. On pthread_mutex_lock it works there...
+    if PTHREAD_LDFLAGS == 'error':
+        if conf.CHECK_FUNCS_IN('pthread_mutex_lock', 'pthread'):
+            PTHREAD_CFLAGS='-D_REENTRANT'
+            PTHREAD_LDFLAGS='-lpthread'
+
+    if PTHREAD_CFLAGS != 'error' and PTHREAD_LDFLAGS != 'error':
+        if conf.CONFIG_SET('replace_add_global_pthread'):
+            conf.ADD_CFLAGS(PTHREAD_CFLAGS)
+            conf.ADD_LDFLAGS(PTHREAD_LDFLAGS)
+        conf.CHECK_HEADERS('pthread.h')
+        conf.DEFINE('HAVE_PTHREAD', '1')
+
+    if conf.CONFIG_SET('HAVE_PTHREAD'):
+
+        conf.CHECK_DECLS('pthread_mutexattr_setrobust', headers='pthread.h')
+        if not conf.CONFIG_SET('HAVE_DECL_PTHREAD_MUTEXATTR_SETROBUST'):
+            conf.CHECK_DECLS('pthread_mutexattr_setrobust_np',
+                             headers='pthread.h')
+
+        conf.CHECK_FUNCS_IN('pthread_mutexattr_setrobust', 'pthread',
+                            checklibc=True, headers='pthread.h')
+        if not conf.CONFIG_SET('HAVE_PTHREAD_MUTEXATTR_SETROBUST'):
+            conf.CHECK_FUNCS_IN('pthread_mutexattr_setrobust_np', 'pthread',
+                                checklibc=True, headers='pthread.h')
+
+        conf.CHECK_DECLS('pthread_mutex_consistent', headers='pthread.h')
+        if not conf.CONFIG_SET('HAVE_DECL_PTHREAD_MUTEX_CONSISTENT'):
+            conf.CHECK_DECLS('pthread_mutex_consistent_np',
+                             headers='pthread.h')
+
+        conf.CHECK_FUNCS_IN('pthread_mutex_consistent', 'pthread',
+                            checklibc=True, headers='pthread.h')
+        if not conf.CONFIG_SET('HAVE_PTHREAD_MUTEX_CONSISTENT'):
+            conf.CHECK_FUNCS_IN('pthread_mutex_consistent_np', 'pthread',
+                                checklibc=True, headers='pthread.h')
+
+        if ((conf.CONFIG_SET('HAVE_PTHREAD_MUTEXATTR_SETROBUST') or
+             conf.CONFIG_SET('HAVE_PTHREAD_MUTEXATTR_SETROBUST_NP')) and
+            (conf.CONFIG_SET('HAVE_PTHREAD_MUTEX_CONSISTENT') or
+             conf.CONFIG_SET('HAVE_PTHREAD_MUTEX_CONSISTENT_NP'))):
+            conf.DEFINE('HAVE_ROBUST_MUTEXES', 1)
+
     conf.CHECK_FUNCS_IN('crypt', 'crypt', checklibc=True)
 
     conf.CHECK_VARIABLE('rl_event_hook', define='HAVE_DECL_RL_EVENT_HOOK', always=True,
@@ -430,12 +482,16 @@ removeea setea
     conf.CHECK_DECLS('snprintf vsnprintf asprintf vasprintf')
 
     conf.CHECK_DECLS('errno', headers='errno.h', reverse=True)
+    conf.CHECK_DECLS('EWOULDBLOCK', headers='errno.h')
     conf.CHECK_DECLS('environ getgrent_r getpwent_r', reverse=True, headers='pwd.h grp.h')
     conf.CHECK_DECLS('pread pwrite setenv setresgid setresuid', reverse=True)
 
     if conf.CONFIG_SET('HAVE_EPOLL_CREATE') and conf.CONFIG_SET('HAVE_SYS_EPOLL_H'):
         conf.DEFINE('HAVE_EPOLL', 1)
 
+    if conf.CONFIG_SET('HAVE_PORT_CREATE') and conf.CONFIG_SET('HAVE_PORT_H'):
+        conf.DEFINE('HAVE_SOLARIS_PORTS', 1)
+
     conf.CHECK_HEADERS('poll.h')
     conf.CHECK_FUNCS('poll')
 
@@ -548,13 +604,6 @@ removeea setea
                     execute=True,
                     mandatory=True) # lets see if we get a mandatory failure for this one
 
-    if conf.CHECK_CFLAGS('-fvisibility=hidden'):
-        conf.env.VISIBILITY_CFLAGS = '-fvisibility=hidden'
-        conf.CHECK_CODE('''void vis_foo1(void) {}
-                           __attribute__((visibility("default"))) void vis_foo2(void) {}''',
-                        cflags=conf.env.VISIBILITY_CFLAGS,
-                        define='HAVE_VISIBILITY_ATTR')
-
     # look for a method of finding the list of network interfaces
     for method in ['HAVE_IFACE_GETIFADDRS', 'HAVE_IFACE_AIX', 'HAVE_IFACE_IFCONF', 'HAVE_IFACE_IFREQ']:
         if conf.CHECK_CODE('''
index fa56ea5678061a21c7e38f25ed5463921d79e761..c10fd53db12b81766dc08f5604686caa6aa2952e 100644 (file)
--- a/talloc.c
+++ b/talloc.c
@@ -991,7 +991,13 @@ static inline int _talloc_free_internal(void *ptr, const char *location)
                }
                tc->destructor = (talloc_destructor_t)-1;
                if (d(ptr) == -1) {
-                       tc->destructor = d;
+                       /*
+                        * Only replace the destructor pointer if
+                        * calling the destructor didn't modify it.
+                        */
+                       if (tc->destructor == (talloc_destructor_t)-1) {
+                               tc->destructor = d;
+                       }
                        return -1;
                }
                tc->destructor = NULL;
@@ -1058,7 +1064,7 @@ static inline int _talloc_free_internal(void *ptr, const char *location)
        return 0;
 }
 
-static size_t _talloc_total_limit_size(const void *ptr,
+static inline size_t _talloc_total_limit_size(const void *ptr,
                                        struct talloc_memlimit *old_limit,
                                        struct talloc_memlimit *new_limit);
 
@@ -1464,6 +1470,13 @@ static inline void _talloc_free_children_internal(struct talloc_chunk *tc,
                        if (p) new_parent = TC_PTR_FROM_CHUNK(p);
                }
                if (unlikely(_talloc_free_internal(child, location) == -1)) {
+                       if (talloc_parent_chunk(child) != tc) {
+                               /*
+                                * Destructor already reparented this child.
+                                * No further reparenting needed.
+                                */
+                               return;
+                       }
                        if (new_parent == null_context) {
                                struct talloc_chunk *p = talloc_parent_chunk(ptr);
                                if (p) new_parent = TC_PTR_FROM_CHUNK(p);
index a878278f16180dd153bef09a4eb248eeab1bbbdf..eb3e13d5af08347a33cb8d2b30e643d332dda442 100644 (file)
@@ -981,6 +981,84 @@ static bool test_free_parent_deny_child(void)
        return true;
 }
 
+struct new_parent {
+       void *new_parent;
+       char val[20];
+};
+
+static int reparenting_destructor(struct new_parent *np)
+{
+       talloc_set_destructor(np, NULL);
+       (void)talloc_move(np->new_parent, &np);
+       return -1;
+}
+
+static bool test_free_parent_reparent_child(void)
+{
+       void *top = talloc_new(NULL);
+       char *level1;
+       char *alternate_level1;
+       char *level2;
+       struct new_parent *level3;
+
+       printf("test: free_parent_reparent_child\n# "
+               "TALLOC FREE PARENT REPARENT CHILD\n");
+
+       level1 = talloc_strdup(top, "level1");
+       alternate_level1 = talloc_strdup(top, "alternate_level1");
+       level2 = talloc_strdup(level1, "level2");
+       level3 = talloc(level2, struct new_parent);
+       level3->new_parent = alternate_level1;
+       memset(level3->val, 'x', sizeof(level3->val));
+
+       talloc_set_destructor(level3, reparenting_destructor);
+       talloc_free(level1);
+
+       CHECK_PARENT("free_parent_reparent_child",
+               level3, alternate_level1);
+
+       talloc_free(top);
+
+       printf("success: free_parent_reparent_child\n");
+       return true;
+}
+
+static bool test_free_parent_reparent_child_in_pool(void)
+{
+       void *top = talloc_new(NULL);
+       char *level1;
+       char *alternate_level1;
+       char *level2;
+       void *pool;
+       struct new_parent *level3;
+
+       printf("test: free_parent_reparent_child_in_pool\n# "
+               "TALLOC FREE PARENT REPARENT CHILD IN POOL\n");
+
+       pool = talloc_pool(top, 1024);
+       level1 = talloc_strdup(pool, "level1");
+       alternate_level1 = talloc_strdup(top, "alternate_level1");
+       level2 = talloc_strdup(level1, "level2");
+       level3 = talloc(level2, struct new_parent);
+       level3->new_parent = alternate_level1;
+       memset(level3->val, 'x', sizeof(level3->val));
+
+       talloc_set_destructor(level3, reparenting_destructor);
+       talloc_free(level1);
+       talloc_set_destructor(level3, NULL);
+
+       CHECK_PARENT("free_parent_reparent_child_in_pool",
+               level3, alternate_level1);
+
+       /* Even freeing alternate_level1 should leave pool alone. */
+       talloc_free(alternate_level1);
+       talloc_free(top);
+
+       printf("success: free_parent_reparent_child_in_pool\n");
+       return true;
+}
+
+
 static bool test_talloc_ptrtype(void)
 {
        void *top = talloc_new(NULL);
@@ -1674,6 +1752,10 @@ bool torture_local_talloc(struct torture_context *tctx)
        test_reset();
        ret &= test_free_parent_deny_child(); 
        test_reset();
+       ret &= test_free_parent_reparent_child();
+       test_reset();
+       ret &= test_free_parent_reparent_child_in_pool();
+       test_reset();
        ret &= test_talloc_ptrtype();
        test_reset();
        ret &= test_talloc_free_in_destructor();
diff --git a/wscript b/wscript
index 9df64d995d862ae4b49614ddbd54df84ac02e20c..97c52c3e3eda948baa7391ce09c7c1373a65824d 100644 (file)
--- a/wscript
+++ b/wscript
@@ -1,7 +1,7 @@
 #!/usr/bin/env python
 
 APPNAME = 'talloc'
-VERSION = '2.1.1'
+VERSION = '2.1.2'
 
 
 blddir = 'bin'
@@ -12,7 +12,7 @@ import os, sys
 # find the buildtools directory
 srcdir = '.'
 while not os.path.exists(srcdir+'/buildtools') and len(srcdir.split('/')) < 5:
-    srcdir = '../' + srcdir
+    srcdir = srcdir + '/..'
 sys.path.insert(0, srcdir + '/buildtools/wafsamba')
 
 import sys