annotate DEPENDENCIES/mingw32/Python27/Lib/site-packages/numpy/distutils/ccompiler.py @ 133:4acb5d8d80b6 tip

Don't fail environmental check if README.md exists (but .txt and no-suffix don't)
author Chris Cannam
date Tue, 30 Jul 2019 12:25:44 +0100
parents 2a2c65a20a8b
children
rev   line source
Chris@87 1 from __future__ import division, absolute_import, print_function
Chris@87 2
Chris@87 3 import re
Chris@87 4 import os
Chris@87 5 import sys
Chris@87 6 import types
Chris@87 7 from copy import copy
Chris@87 8
Chris@87 9 from distutils.ccompiler import *
Chris@87 10 from distutils import ccompiler
Chris@87 11 from distutils.errors import DistutilsExecError, DistutilsModuleError, \
Chris@87 12 DistutilsPlatformError
Chris@87 13 from distutils.sysconfig import customize_compiler
Chris@87 14 from distutils.version import LooseVersion
Chris@87 15
Chris@87 16 from numpy.distutils import log
Chris@87 17 from numpy.distutils.exec_command import exec_command
Chris@87 18 from numpy.distutils.misc_util import cyg2win32, is_sequence, mingw32, \
Chris@87 19 quote_args
Chris@87 20 from numpy.distutils.compat import get_exception
Chris@87 21
Chris@87 22
Chris@87 23 def replace_method(klass, method_name, func):
Chris@87 24 if sys.version_info[0] < 3:
Chris@87 25 m = types.MethodType(func, None, klass)
Chris@87 26 else:
Chris@87 27 # Py3k does not have unbound method anymore, MethodType does not work
Chris@87 28 m = lambda self, *args, **kw: func(self, *args, **kw)
Chris@87 29 setattr(klass, method_name, m)
Chris@87 30
Chris@87 31 # Using customized CCompiler.spawn.
Chris@87 32 def CCompiler_spawn(self, cmd, display=None):
Chris@87 33 """
Chris@87 34 Execute a command in a sub-process.
Chris@87 35
Chris@87 36 Parameters
Chris@87 37 ----------
Chris@87 38 cmd : str
Chris@87 39 The command to execute.
Chris@87 40 display : str or sequence of str, optional
Chris@87 41 The text to add to the log file kept by `numpy.distutils`.
Chris@87 42 If not given, `display` is equal to `cmd`.
Chris@87 43
Chris@87 44 Returns
Chris@87 45 -------
Chris@87 46 None
Chris@87 47
Chris@87 48 Raises
Chris@87 49 ------
Chris@87 50 DistutilsExecError
Chris@87 51 If the command failed, i.e. the exit status was not 0.
Chris@87 52
Chris@87 53 """
Chris@87 54 if display is None:
Chris@87 55 display = cmd
Chris@87 56 if is_sequence(display):
Chris@87 57 display = ' '.join(list(display))
Chris@87 58 log.info(display)
Chris@87 59 s, o = exec_command(cmd)
Chris@87 60 if s:
Chris@87 61 if is_sequence(cmd):
Chris@87 62 cmd = ' '.join(list(cmd))
Chris@87 63 try:
Chris@87 64 print(o)
Chris@87 65 except UnicodeError:
Chris@87 66 # When installing through pip, `o` can contain non-ascii chars
Chris@87 67 pass
Chris@87 68 if re.search('Too many open files', o):
Chris@87 69 msg = '\nTry rerunning setup command until build succeeds.'
Chris@87 70 else:
Chris@87 71 msg = ''
Chris@87 72 raise DistutilsExecError('Command "%s" failed with exit status %d%s' % (cmd, s, msg))
Chris@87 73
Chris@87 74 replace_method(CCompiler, 'spawn', CCompiler_spawn)
Chris@87 75
Chris@87 76 def CCompiler_object_filenames(self, source_filenames, strip_dir=0, output_dir=''):
Chris@87 77 """
Chris@87 78 Return the name of the object files for the given source files.
Chris@87 79
Chris@87 80 Parameters
Chris@87 81 ----------
Chris@87 82 source_filenames : list of str
Chris@87 83 The list of paths to source files. Paths can be either relative or
Chris@87 84 absolute, this is handled transparently.
Chris@87 85 strip_dir : bool, optional
Chris@87 86 Whether to strip the directory from the returned paths. If True,
Chris@87 87 the file name prepended by `output_dir` is returned. Default is False.
Chris@87 88 output_dir : str, optional
Chris@87 89 If given, this path is prepended to the returned paths to the
Chris@87 90 object files.
Chris@87 91
Chris@87 92 Returns
Chris@87 93 -------
Chris@87 94 obj_names : list of str
Chris@87 95 The list of paths to the object files corresponding to the source
Chris@87 96 files in `source_filenames`.
Chris@87 97
Chris@87 98 """
Chris@87 99 if output_dir is None:
Chris@87 100 output_dir = ''
Chris@87 101 obj_names = []
Chris@87 102 for src_name in source_filenames:
Chris@87 103 base, ext = os.path.splitext(os.path.normpath(src_name))
Chris@87 104 base = os.path.splitdrive(base)[1] # Chop off the drive
Chris@87 105 base = base[os.path.isabs(base):] # If abs, chop off leading /
Chris@87 106 if base.startswith('..'):
Chris@87 107 # Resolve starting relative path components, middle ones
Chris@87 108 # (if any) have been handled by os.path.normpath above.
Chris@87 109 i = base.rfind('..')+2
Chris@87 110 d = base[:i]
Chris@87 111 d = os.path.basename(os.path.abspath(d))
Chris@87 112 base = d + base[i:]
Chris@87 113 if ext not in self.src_extensions:
Chris@87 114 raise UnknownFileError("unknown file type '%s' (from '%s')" % (ext, src_name))
Chris@87 115 if strip_dir:
Chris@87 116 base = os.path.basename(base)
Chris@87 117 obj_name = os.path.join(output_dir, base + self.obj_extension)
Chris@87 118 obj_names.append(obj_name)
Chris@87 119 return obj_names
Chris@87 120
Chris@87 121 replace_method(CCompiler, 'object_filenames', CCompiler_object_filenames)
Chris@87 122
Chris@87 123 def CCompiler_compile(self, sources, output_dir=None, macros=None,
Chris@87 124 include_dirs=None, debug=0, extra_preargs=None,
Chris@87 125 extra_postargs=None, depends=None):
Chris@87 126 """
Chris@87 127 Compile one or more source files.
Chris@87 128
Chris@87 129 Please refer to the Python distutils API reference for more details.
Chris@87 130
Chris@87 131 Parameters
Chris@87 132 ----------
Chris@87 133 sources : list of str
Chris@87 134 A list of filenames
Chris@87 135 output_dir : str, optional
Chris@87 136 Path to the output directory.
Chris@87 137 macros : list of tuples
Chris@87 138 A list of macro definitions.
Chris@87 139 include_dirs : list of str, optional
Chris@87 140 The directories to add to the default include file search path for
Chris@87 141 this compilation only.
Chris@87 142 debug : bool, optional
Chris@87 143 Whether or not to output debug symbols in or alongside the object
Chris@87 144 file(s).
Chris@87 145 extra_preargs, extra_postargs : ?
Chris@87 146 Extra pre- and post-arguments.
Chris@87 147 depends : list of str, optional
Chris@87 148 A list of file names that all targets depend on.
Chris@87 149
Chris@87 150 Returns
Chris@87 151 -------
Chris@87 152 objects : list of str
Chris@87 153 A list of object file names, one per source file `sources`.
Chris@87 154
Chris@87 155 Raises
Chris@87 156 ------
Chris@87 157 CompileError
Chris@87 158 If compilation fails.
Chris@87 159
Chris@87 160 """
Chris@87 161 # This method is effective only with Python >=2.3 distutils.
Chris@87 162 # Any changes here should be applied also to fcompiler.compile
Chris@87 163 # method to support pre Python 2.3 distutils.
Chris@87 164 if not sources:
Chris@87 165 return []
Chris@87 166 # FIXME:RELATIVE_IMPORT
Chris@87 167 if sys.version_info[0] < 3:
Chris@87 168 from .fcompiler import FCompiler
Chris@87 169 else:
Chris@87 170 from numpy.distutils.fcompiler import FCompiler
Chris@87 171 if isinstance(self, FCompiler):
Chris@87 172 display = []
Chris@87 173 for fc in ['f77', 'f90', 'fix']:
Chris@87 174 fcomp = getattr(self, 'compiler_'+fc)
Chris@87 175 if fcomp is None:
Chris@87 176 continue
Chris@87 177 display.append("Fortran %s compiler: %s" % (fc, ' '.join(fcomp)))
Chris@87 178 display = '\n'.join(display)
Chris@87 179 else:
Chris@87 180 ccomp = self.compiler_so
Chris@87 181 display = "C compiler: %s\n" % (' '.join(ccomp),)
Chris@87 182 log.info(display)
Chris@87 183 macros, objects, extra_postargs, pp_opts, build = \
Chris@87 184 self._setup_compile(output_dir, macros, include_dirs, sources,
Chris@87 185 depends, extra_postargs)
Chris@87 186 cc_args = self._get_cc_args(pp_opts, debug, extra_preargs)
Chris@87 187 display = "compile options: '%s'" % (' '.join(cc_args))
Chris@87 188 if extra_postargs:
Chris@87 189 display += "\nextra options: '%s'" % (' '.join(extra_postargs))
Chris@87 190 log.info(display)
Chris@87 191
Chris@87 192 # build any sources in same order as they were originally specified
Chris@87 193 # especially important for fortran .f90 files using modules
Chris@87 194 if isinstance(self, FCompiler):
Chris@87 195 objects_to_build = list(build.keys())
Chris@87 196 for obj in objects:
Chris@87 197 if obj in objects_to_build:
Chris@87 198 src, ext = build[obj]
Chris@87 199 if self.compiler_type=='absoft':
Chris@87 200 obj = cyg2win32(obj)
Chris@87 201 src = cyg2win32(src)
Chris@87 202 self._compile(obj, src, ext, cc_args, extra_postargs, pp_opts)
Chris@87 203 else:
Chris@87 204 for obj, (src, ext) in build.items():
Chris@87 205 self._compile(obj, src, ext, cc_args, extra_postargs, pp_opts)
Chris@87 206
Chris@87 207 # Return *all* object filenames, not just the ones we just built.
Chris@87 208 return objects
Chris@87 209
Chris@87 210 replace_method(CCompiler, 'compile', CCompiler_compile)
Chris@87 211
Chris@87 212 def CCompiler_customize_cmd(self, cmd, ignore=()):
Chris@87 213 """
Chris@87 214 Customize compiler using distutils command.
Chris@87 215
Chris@87 216 Parameters
Chris@87 217 ----------
Chris@87 218 cmd : class instance
Chris@87 219 An instance inheriting from `distutils.cmd.Command`.
Chris@87 220 ignore : sequence of str, optional
Chris@87 221 List of `CCompiler` commands (without ``'set_'``) that should not be
Chris@87 222 altered. Strings that are checked for are:
Chris@87 223 ``('include_dirs', 'define', 'undef', 'libraries', 'library_dirs',
Chris@87 224 'rpath', 'link_objects')``.
Chris@87 225
Chris@87 226 Returns
Chris@87 227 -------
Chris@87 228 None
Chris@87 229
Chris@87 230 """
Chris@87 231 log.info('customize %s using %s' % (self.__class__.__name__,
Chris@87 232 cmd.__class__.__name__))
Chris@87 233 def allow(attr):
Chris@87 234 return getattr(cmd, attr, None) is not None and attr not in ignore
Chris@87 235
Chris@87 236 if allow('include_dirs'):
Chris@87 237 self.set_include_dirs(cmd.include_dirs)
Chris@87 238 if allow('define'):
Chris@87 239 for (name, value) in cmd.define:
Chris@87 240 self.define_macro(name, value)
Chris@87 241 if allow('undef'):
Chris@87 242 for macro in cmd.undef:
Chris@87 243 self.undefine_macro(macro)
Chris@87 244 if allow('libraries'):
Chris@87 245 self.set_libraries(self.libraries + cmd.libraries)
Chris@87 246 if allow('library_dirs'):
Chris@87 247 self.set_library_dirs(self.library_dirs + cmd.library_dirs)
Chris@87 248 if allow('rpath'):
Chris@87 249 self.set_runtime_library_dirs(cmd.rpath)
Chris@87 250 if allow('link_objects'):
Chris@87 251 self.set_link_objects(cmd.link_objects)
Chris@87 252
Chris@87 253 replace_method(CCompiler, 'customize_cmd', CCompiler_customize_cmd)
Chris@87 254
Chris@87 255 def _compiler_to_string(compiler):
Chris@87 256 props = []
Chris@87 257 mx = 0
Chris@87 258 keys = list(compiler.executables.keys())
Chris@87 259 for key in ['version', 'libraries', 'library_dirs',
Chris@87 260 'object_switch', 'compile_switch',
Chris@87 261 'include_dirs', 'define', 'undef', 'rpath', 'link_objects']:
Chris@87 262 if key not in keys:
Chris@87 263 keys.append(key)
Chris@87 264 for key in keys:
Chris@87 265 if hasattr(compiler, key):
Chris@87 266 v = getattr(compiler, key)
Chris@87 267 mx = max(mx, len(key))
Chris@87 268 props.append((key, repr(v)))
Chris@87 269 lines = []
Chris@87 270 format = '%-' + repr(mx+1) + 's = %s'
Chris@87 271 for prop in props:
Chris@87 272 lines.append(format % prop)
Chris@87 273 return '\n'.join(lines)
Chris@87 274
Chris@87 275 def CCompiler_show_customization(self):
Chris@87 276 """
Chris@87 277 Print the compiler customizations to stdout.
Chris@87 278
Chris@87 279 Parameters
Chris@87 280 ----------
Chris@87 281 None
Chris@87 282
Chris@87 283 Returns
Chris@87 284 -------
Chris@87 285 None
Chris@87 286
Chris@87 287 Notes
Chris@87 288 -----
Chris@87 289 Printing is only done if the distutils log threshold is < 2.
Chris@87 290
Chris@87 291 """
Chris@87 292 if 0:
Chris@87 293 for attrname in ['include_dirs', 'define', 'undef',
Chris@87 294 'libraries', 'library_dirs',
Chris@87 295 'rpath', 'link_objects']:
Chris@87 296 attr = getattr(self, attrname, None)
Chris@87 297 if not attr:
Chris@87 298 continue
Chris@87 299 log.info("compiler '%s' is set to %s" % (attrname, attr))
Chris@87 300 try:
Chris@87 301 self.get_version()
Chris@87 302 except:
Chris@87 303 pass
Chris@87 304 if log._global_log.threshold<2:
Chris@87 305 print('*'*80)
Chris@87 306 print(self.__class__)
Chris@87 307 print(_compiler_to_string(self))
Chris@87 308 print('*'*80)
Chris@87 309
Chris@87 310 replace_method(CCompiler, 'show_customization', CCompiler_show_customization)
Chris@87 311
Chris@87 312 def CCompiler_customize(self, dist, need_cxx=0):
Chris@87 313 """
Chris@87 314 Do any platform-specific customization of a compiler instance.
Chris@87 315
Chris@87 316 This method calls `distutils.sysconfig.customize_compiler` for
Chris@87 317 platform-specific customization, as well as optionally remove a flag
Chris@87 318 to suppress spurious warnings in case C++ code is being compiled.
Chris@87 319
Chris@87 320 Parameters
Chris@87 321 ----------
Chris@87 322 dist : object
Chris@87 323 This parameter is not used for anything.
Chris@87 324 need_cxx : bool, optional
Chris@87 325 Whether or not C++ has to be compiled. If so (True), the
Chris@87 326 ``"-Wstrict-prototypes"`` option is removed to prevent spurious
Chris@87 327 warnings. Default is False.
Chris@87 328
Chris@87 329 Returns
Chris@87 330 -------
Chris@87 331 None
Chris@87 332
Chris@87 333 Notes
Chris@87 334 -----
Chris@87 335 All the default options used by distutils can be extracted with::
Chris@87 336
Chris@87 337 from distutils import sysconfig
Chris@87 338 sysconfig.get_config_vars('CC', 'CXX', 'OPT', 'BASECFLAGS',
Chris@87 339 'CCSHARED', 'LDSHARED', 'SO')
Chris@87 340
Chris@87 341 """
Chris@87 342 # See FCompiler.customize for suggested usage.
Chris@87 343 log.info('customize %s' % (self.__class__.__name__))
Chris@87 344 customize_compiler(self)
Chris@87 345 if need_cxx:
Chris@87 346 # In general, distutils uses -Wstrict-prototypes, but this option is
Chris@87 347 # not valid for C++ code, only for C. Remove it if it's there to
Chris@87 348 # avoid a spurious warning on every compilation.
Chris@87 349 try:
Chris@87 350 self.compiler_so.remove('-Wstrict-prototypes')
Chris@87 351 except (AttributeError, ValueError):
Chris@87 352 pass
Chris@87 353
Chris@87 354 if hasattr(self, 'compiler') and 'cc' in self.compiler[0]:
Chris@87 355 if not self.compiler_cxx:
Chris@87 356 if self.compiler[0].startswith('gcc'):
Chris@87 357 a, b = 'gcc', 'g++'
Chris@87 358 else:
Chris@87 359 a, b = 'cc', 'c++'
Chris@87 360 self.compiler_cxx = [self.compiler[0].replace(a, b)]\
Chris@87 361 + self.compiler[1:]
Chris@87 362 else:
Chris@87 363 if hasattr(self, 'compiler'):
Chris@87 364 log.warn("#### %s #######" % (self.compiler,))
Chris@87 365 log.warn('Missing compiler_cxx fix for '+self.__class__.__name__)
Chris@87 366 return
Chris@87 367
Chris@87 368 replace_method(CCompiler, 'customize', CCompiler_customize)
Chris@87 369
Chris@87 370 def simple_version_match(pat=r'[-.\d]+', ignore='', start=''):
Chris@87 371 """
Chris@87 372 Simple matching of version numbers, for use in CCompiler and FCompiler.
Chris@87 373
Chris@87 374 Parameters
Chris@87 375 ----------
Chris@87 376 pat : str, optional
Chris@87 377 A regular expression matching version numbers.
Chris@87 378 Default is ``r'[-.\\d]+'``.
Chris@87 379 ignore : str, optional
Chris@87 380 A regular expression matching patterns to skip.
Chris@87 381 Default is ``''``, in which case nothing is skipped.
Chris@87 382 start : str, optional
Chris@87 383 A regular expression matching the start of where to start looking
Chris@87 384 for version numbers.
Chris@87 385 Default is ``''``, in which case searching is started at the
Chris@87 386 beginning of the version string given to `matcher`.
Chris@87 387
Chris@87 388 Returns
Chris@87 389 -------
Chris@87 390 matcher : callable
Chris@87 391 A function that is appropriate to use as the ``.version_match``
Chris@87 392 attribute of a `CCompiler` class. `matcher` takes a single parameter,
Chris@87 393 a version string.
Chris@87 394
Chris@87 395 """
Chris@87 396 def matcher(self, version_string):
Chris@87 397 # version string may appear in the second line, so getting rid
Chris@87 398 # of new lines:
Chris@87 399 version_string = version_string.replace('\n', ' ')
Chris@87 400 pos = 0
Chris@87 401 if start:
Chris@87 402 m = re.match(start, version_string)
Chris@87 403 if not m:
Chris@87 404 return None
Chris@87 405 pos = m.end()
Chris@87 406 while True:
Chris@87 407 m = re.search(pat, version_string[pos:])
Chris@87 408 if not m:
Chris@87 409 return None
Chris@87 410 if ignore and re.match(ignore, m.group(0)):
Chris@87 411 pos = m.end()
Chris@87 412 continue
Chris@87 413 break
Chris@87 414 return m.group(0)
Chris@87 415 return matcher
Chris@87 416
Chris@87 417 def CCompiler_get_version(self, force=False, ok_status=[0]):
Chris@87 418 """
Chris@87 419 Return compiler version, or None if compiler is not available.
Chris@87 420
Chris@87 421 Parameters
Chris@87 422 ----------
Chris@87 423 force : bool, optional
Chris@87 424 If True, force a new determination of the version, even if the
Chris@87 425 compiler already has a version attribute. Default is False.
Chris@87 426 ok_status : list of int, optional
Chris@87 427 The list of status values returned by the version look-up process
Chris@87 428 for which a version string is returned. If the status value is not
Chris@87 429 in `ok_status`, None is returned. Default is ``[0]``.
Chris@87 430
Chris@87 431 Returns
Chris@87 432 -------
Chris@87 433 version : str or None
Chris@87 434 Version string, in the format of `distutils.version.LooseVersion`.
Chris@87 435
Chris@87 436 """
Chris@87 437 if not force and hasattr(self, 'version'):
Chris@87 438 return self.version
Chris@87 439 self.find_executables()
Chris@87 440 try:
Chris@87 441 version_cmd = self.version_cmd
Chris@87 442 except AttributeError:
Chris@87 443 return None
Chris@87 444 if not version_cmd or not version_cmd[0]:
Chris@87 445 return None
Chris@87 446 try:
Chris@87 447 matcher = self.version_match
Chris@87 448 except AttributeError:
Chris@87 449 try:
Chris@87 450 pat = self.version_pattern
Chris@87 451 except AttributeError:
Chris@87 452 return None
Chris@87 453 def matcher(version_string):
Chris@87 454 m = re.match(pat, version_string)
Chris@87 455 if not m:
Chris@87 456 return None
Chris@87 457 version = m.group('version')
Chris@87 458 return version
Chris@87 459
Chris@87 460 status, output = exec_command(version_cmd, use_tee=0)
Chris@87 461
Chris@87 462 version = None
Chris@87 463 if status in ok_status:
Chris@87 464 version = matcher(output)
Chris@87 465 if version:
Chris@87 466 version = LooseVersion(version)
Chris@87 467 self.version = version
Chris@87 468 return version
Chris@87 469
Chris@87 470 replace_method(CCompiler, 'get_version', CCompiler_get_version)
Chris@87 471
Chris@87 472 def CCompiler_cxx_compiler(self):
Chris@87 473 """
Chris@87 474 Return the C++ compiler.
Chris@87 475
Chris@87 476 Parameters
Chris@87 477 ----------
Chris@87 478 None
Chris@87 479
Chris@87 480 Returns
Chris@87 481 -------
Chris@87 482 cxx : class instance
Chris@87 483 The C++ compiler, as a `CCompiler` instance.
Chris@87 484
Chris@87 485 """
Chris@87 486 if self.compiler_type=='msvc': return self
Chris@87 487 cxx = copy(self)
Chris@87 488 cxx.compiler_so = [cxx.compiler_cxx[0]] + cxx.compiler_so[1:]
Chris@87 489 if sys.platform.startswith('aix') and 'ld_so_aix' in cxx.linker_so[0]:
Chris@87 490 # AIX needs the ld_so_aix script included with Python
Chris@87 491 cxx.linker_so = [cxx.linker_so[0], cxx.compiler_cxx[0]] \
Chris@87 492 + cxx.linker_so[2:]
Chris@87 493 else:
Chris@87 494 cxx.linker_so = [cxx.compiler_cxx[0]] + cxx.linker_so[1:]
Chris@87 495 return cxx
Chris@87 496
Chris@87 497 replace_method(CCompiler, 'cxx_compiler', CCompiler_cxx_compiler)
Chris@87 498
Chris@87 499 compiler_class['intel'] = ('intelccompiler', 'IntelCCompiler',
Chris@87 500 "Intel C Compiler for 32-bit applications")
Chris@87 501 compiler_class['intele'] = ('intelccompiler', 'IntelItaniumCCompiler',
Chris@87 502 "Intel C Itanium Compiler for Itanium-based applications")
Chris@87 503 compiler_class['intelem'] = ('intelccompiler', 'IntelEM64TCCompiler',
Chris@87 504 "Intel C Compiler for 64-bit applications")
Chris@87 505 compiler_class['pathcc'] = ('pathccompiler', 'PathScaleCCompiler',
Chris@87 506 "PathScale Compiler for SiCortex-based applications")
Chris@87 507 ccompiler._default_compilers += (('linux.*', 'intel'),
Chris@87 508 ('linux.*', 'intele'),
Chris@87 509 ('linux.*', 'intelem'),
Chris@87 510 ('linux.*', 'pathcc'))
Chris@87 511
Chris@87 512 if sys.platform == 'win32':
Chris@87 513 compiler_class['mingw32'] = ('mingw32ccompiler', 'Mingw32CCompiler',
Chris@87 514 "Mingw32 port of GNU C Compiler for Win32"\
Chris@87 515 "(for MSC built Python)")
Chris@87 516 if mingw32():
Chris@87 517 # On windows platforms, we want to default to mingw32 (gcc)
Chris@87 518 # because msvc can't build blitz stuff.
Chris@87 519 log.info('Setting mingw32 as default compiler for nt.')
Chris@87 520 ccompiler._default_compilers = (('nt', 'mingw32'),) \
Chris@87 521 + ccompiler._default_compilers
Chris@87 522
Chris@87 523
Chris@87 524 _distutils_new_compiler = new_compiler
Chris@87 525 def new_compiler (plat=None,
Chris@87 526 compiler=None,
Chris@87 527 verbose=0,
Chris@87 528 dry_run=0,
Chris@87 529 force=0):
Chris@87 530 # Try first C compilers from numpy.distutils.
Chris@87 531 if plat is None:
Chris@87 532 plat = os.name
Chris@87 533 try:
Chris@87 534 if compiler is None:
Chris@87 535 compiler = get_default_compiler(plat)
Chris@87 536 (module_name, class_name, long_description) = compiler_class[compiler]
Chris@87 537 except KeyError:
Chris@87 538 msg = "don't know how to compile C/C++ code on platform '%s'" % plat
Chris@87 539 if compiler is not None:
Chris@87 540 msg = msg + " with '%s' compiler" % compiler
Chris@87 541 raise DistutilsPlatformError(msg)
Chris@87 542 module_name = "numpy.distutils." + module_name
Chris@87 543 try:
Chris@87 544 __import__ (module_name)
Chris@87 545 except ImportError:
Chris@87 546 msg = str(get_exception())
Chris@87 547 log.info('%s in numpy.distutils; trying from distutils',
Chris@87 548 str(msg))
Chris@87 549 module_name = module_name[6:]
Chris@87 550 try:
Chris@87 551 __import__(module_name)
Chris@87 552 except ImportError:
Chris@87 553 msg = str(get_exception())
Chris@87 554 raise DistutilsModuleError("can't compile C/C++ code: unable to load module '%s'" % \
Chris@87 555 module_name)
Chris@87 556 try:
Chris@87 557 module = sys.modules[module_name]
Chris@87 558 klass = vars(module)[class_name]
Chris@87 559 except KeyError:
Chris@87 560 raise DistutilsModuleError(("can't compile C/C++ code: unable to find class '%s' " +
Chris@87 561 "in module '%s'") % (class_name, module_name))
Chris@87 562 compiler = klass(None, dry_run, force)
Chris@87 563 log.debug('new_compiler returns %s' % (klass))
Chris@87 564 return compiler
Chris@87 565
Chris@87 566 ccompiler.new_compiler = new_compiler
Chris@87 567
Chris@87 568 _distutils_gen_lib_options = gen_lib_options
Chris@87 569 def gen_lib_options(compiler, library_dirs, runtime_library_dirs, libraries):
Chris@87 570 library_dirs = quote_args(library_dirs)
Chris@87 571 runtime_library_dirs = quote_args(runtime_library_dirs)
Chris@87 572 r = _distutils_gen_lib_options(compiler, library_dirs,
Chris@87 573 runtime_library_dirs, libraries)
Chris@87 574 lib_opts = []
Chris@87 575 for i in r:
Chris@87 576 if is_sequence(i):
Chris@87 577 lib_opts.extend(list(i))
Chris@87 578 else:
Chris@87 579 lib_opts.append(i)
Chris@87 580 return lib_opts
Chris@87 581 ccompiler.gen_lib_options = gen_lib_options
Chris@87 582
Chris@87 583 # Also fix up the various compiler modules, which do
Chris@87 584 # from distutils.ccompiler import gen_lib_options
Chris@87 585 # Don't bother with mwerks, as we don't support Classic Mac.
Chris@87 586 for _cc in ['msvc', 'bcpp', 'cygwinc', 'emxc', 'unixc']:
Chris@87 587 _m = sys.modules.get('distutils.'+_cc+'compiler')
Chris@87 588 if _m is not None:
Chris@87 589 setattr(_m, 'gen_lib_options', gen_lib_options)
Chris@87 590
Chris@87 591 _distutils_gen_preprocess_options = gen_preprocess_options
Chris@87 592 def gen_preprocess_options (macros, include_dirs):
Chris@87 593 include_dirs = quote_args(include_dirs)
Chris@87 594 return _distutils_gen_preprocess_options(macros, include_dirs)
Chris@87 595 ccompiler.gen_preprocess_options = gen_preprocess_options
Chris@87 596
Chris@87 597 ##Fix distutils.util.split_quoted:
Chris@87 598 # NOTE: I removed this fix in revision 4481 (see ticket #619), but it appears
Chris@87 599 # that removing this fix causes f2py problems on Windows XP (see ticket #723).
Chris@87 600 # Specifically, on WinXP when gfortran is installed in a directory path, which
Chris@87 601 # contains spaces, then f2py is unable to find it.
Chris@87 602 import re
Chris@87 603 import string
Chris@87 604 _wordchars_re = re.compile(r'[^\\\'\"%s ]*' % string.whitespace)
Chris@87 605 _squote_re = re.compile(r"'(?:[^'\\]|\\.)*'")
Chris@87 606 _dquote_re = re.compile(r'"(?:[^"\\]|\\.)*"')
Chris@87 607 _has_white_re = re.compile(r'\s')
Chris@87 608 def split_quoted(s):
Chris@87 609 s = s.strip()
Chris@87 610 words = []
Chris@87 611 pos = 0
Chris@87 612
Chris@87 613 while s:
Chris@87 614 m = _wordchars_re.match(s, pos)
Chris@87 615 end = m.end()
Chris@87 616 if end == len(s):
Chris@87 617 words.append(s[:end])
Chris@87 618 break
Chris@87 619
Chris@87 620 if s[end] in string.whitespace: # unescaped, unquoted whitespace: now
Chris@87 621 words.append(s[:end]) # we definitely have a word delimiter
Chris@87 622 s = s[end:].lstrip()
Chris@87 623 pos = 0
Chris@87 624
Chris@87 625 elif s[end] == '\\': # preserve whatever is being escaped;
Chris@87 626 # will become part of the current word
Chris@87 627 s = s[:end] + s[end+1:]
Chris@87 628 pos = end+1
Chris@87 629
Chris@87 630 else:
Chris@87 631 if s[end] == "'": # slurp singly-quoted string
Chris@87 632 m = _squote_re.match(s, end)
Chris@87 633 elif s[end] == '"': # slurp doubly-quoted string
Chris@87 634 m = _dquote_re.match(s, end)
Chris@87 635 else:
Chris@87 636 raise RuntimeError("this can't happen (bad char '%c')" % s[end])
Chris@87 637
Chris@87 638 if m is None:
Chris@87 639 raise ValueError("bad string (mismatched %s quotes?)" % s[end])
Chris@87 640
Chris@87 641 (beg, end) = m.span()
Chris@87 642 if _has_white_re.search(s[beg+1:end-1]):
Chris@87 643 s = s[:beg] + s[beg+1:end-1] + s[end:]
Chris@87 644 pos = m.end() - 2
Chris@87 645 else:
Chris@87 646 # Keeping quotes when a quoted word does not contain
Chris@87 647 # white-space. XXX: send a patch to distutils
Chris@87 648 pos = m.end()
Chris@87 649
Chris@87 650 if pos >= len(s):
Chris@87 651 words.append(s)
Chris@87 652 break
Chris@87 653
Chris@87 654 return words
Chris@87 655 ccompiler.split_quoted = split_quoted
Chris@87 656 ##Fix distutils.util.split_quoted: