Exemplo n.º 1
0
 def build(self, noerr=False):
     basename = self.outputfilename.new(ext='')
     data = ''
     try:
         saved_environ = os.environ.copy()
         try:
             c = stdoutcapture.Capture(mixed_out_err=True)
             self._build()
         finally:
             # workaround for a distutils bugs where some env vars can
             # become longer and longer every time it is used
             for key, value in saved_environ.items():
                 if os.environ.get(key) != value:
                     os.environ[key] = value
             foutput, foutput = c.done()
             data = foutput.read()
             if data:
                 fdump = basename.new(ext='errors').open("w")
                 fdump.write(data)
                 fdump.close()
     except:
         if not noerr:
             print >> sys.stderr, data
         raise
Exemplo n.º 2
0
def compile_c_module(cfiles, modbasename, eci, tmpdir=None):
    #try:
    #    from distutils.log import set_threshold
    #    set_threshold(10000)
    #except ImportError:
    #    print "ERROR IMPORTING"
    #    pass
    cfiles = [py.path.local(f) for f in cfiles]
    if tmpdir is None:
        tmpdir = configdir.join("module_cache").ensure(dir=1)
    num = 0
    cfiles += eci.separate_module_files
    include_dirs = list(eci.include_dirs)
    library_dirs = list(eci.library_dirs)
    if sys.platform == 'darwin':  # support Fink & Darwinports
        for s in ('/sw/', '/opt/local/'):
            if s + 'include' not in include_dirs and \
               os.path.exists(s + 'include'):
                include_dirs.append(s + 'include')
            if s + 'lib' not in library_dirs and \
               os.path.exists(s + 'lib'):
                library_dirs.append(s + 'lib')

    num = 0
    modname = modbasename
    while 1:
        if not tmpdir.join(modname + so_ext).check():
            break
        num += 1
        modname = '%s_%d' % (modbasename, num)

    lastdir = tmpdir.chdir()
    libraries = eci.libraries
    ensure_correct_math()
    try:
        if debug: print "modname", modname
        c = stdoutcapture.Capture(mixed_out_err=True)
        try:
            try:
                if compiler_command():
                    # GCC-ish options only
                    from distutils import sysconfig
                    gcv = sysconfig.get_config_vars()
                    cmd = compiler_command().replace('%s',
                                                     str(tmpdir.join(modname)))
                    for dir in [gcv['INCLUDEPY']] + list(include_dirs):
                        cmd += ' -I%s' % dir
                    for dir in library_dirs:
                        cmd += ' -L%s' % dir
                    os.system(cmd)
                else:
                    from distutils.dist import Distribution
                    from distutils.extension import Extension
                    from distutils.ccompiler import get_default_compiler
                    saved_environ = os.environ.items()
                    try:
                        # distutils.core.setup() is really meant for end-user
                        # interactive usage, because it eats most exceptions and
                        # turn them into SystemExits.  Instead, we directly
                        # instantiate a Distribution, which also allows us to
                        # ignore unwanted features like config files.
                        extra_compile_args = []
                        # ensure correct math on windows
                        if sys.platform == 'win32':
                            extra_compile_args.append(
                                '/Op')  # get extra precision
                        if get_default_compiler() == 'unix':
                            old_version = False
                            try:
                                g = os.popen('gcc --version', 'r')
                                verinfo = g.read()
                                g.close()
                            except (OSError, IOError):
                                pass
                            else:
                                old_version = verinfo.startswith('2')
                            if not old_version:
                                extra_compile_args.extend([
                                    "-Wno-unused-label", "-Wno-unused-variable"
                                ])
                        attrs = {
                            'name':
                            "testmodule",
                            'ext_modules': [
                                Extension(
                                    modname,
                                    [str(cfile) for cfile in cfiles],
                                    include_dirs=include_dirs,
                                    library_dirs=library_dirs,
                                    extra_compile_args=extra_compile_args,
                                    libraries=list(libraries),
                                )
                            ],
                            'script_name':
                            'setup.py',
                            'script_args':
                            ['-q', 'build_ext', '--inplace', '--force'],
                        }
                        dist = Distribution(attrs)
                        if not dist.parse_command_line():
                            raise ValueError, "distutils cmdline parse error"
                        dist.run_commands()
                    finally:
                        for key, value in saved_environ:
                            if os.environ.get(key) != value:
                                os.environ[key] = value
            finally:
                foutput, foutput = c.done()
                data = foutput.read()
                if data:
                    fdump = open("%s.errors" % modname, "w")
                    fdump.write(data)
                    fdump.close()
            # XXX do we need to do some check on fout/ferr?
            # XXX not a nice way to import a module
        except:
            print >> sys.stderr, data
            raise
    finally:
        lastdir.chdir()
    return str(tmpdir.join(modname) + so_ext)