3
5^l                 @   s  d dl mZmZmZ d dlZd dlZd dlZd dlZd dlZd dl	Z	d dl
Z
d dlmZ d dlmZ d dlT d dlmZmZmZmZ d dlmZ d dlmZ d d	lmZ d d
lmZ d dlmZmZ d dlm Z m!Z!m"Z"m#Z#m$Z$ yd dl%Z%W n e&k
r
   d dl'Z%Y nX da(e%j) Z*e+ Z,dd Z-dd Z.dd Z/e.e0de/ d\ddZ1e.e0de1 d]ddZ2e.e0de2 d^ddZ3e.e0de3 f fddZ4e.e0d e4 d!d" Z5d#d$ Z6e.e0d%e6 d_d&d'Z7e.e0d(e7 d`d*d+Z8d,d gfd-d.Z9e.e0d/e9 d0d1 Z:e.e0d2e: dae;d6< dbe;d9< dce;d<< dde;d?< dee;dB< dfe;dF< e j<dm7  _<ej=dIkrxdne;dM< e" rxej>dN dpej< e_<e?Z@dqdOdPZ?e?e_?eAZBdQdR ZAeAe_Ax8drD ]0ZCejDjEdZeC d[ ZFeFdk	reGeFdReA qW dS )s    )divisionabsolute_importprint_functionN)copy)	ccompiler)*)DistutilsExecErrorDistutilsModuleErrorDistutilsPlatformErrorCompileError)customize_compiler)LooseVersion)log)get_exception)filepath_from_subprocess_outputforward_bytes_to_stdout)	cyg2win32is_sequencemingw32get_num_build_jobs_commandline_dep_stringc             C   s   | d }t jj|sdS t|d}|j }W dQ R X t|||}|d }||krVdS dj|dd }	dd tj|	dd	D }
y2t j	| j
}x |
D ]}t j	|j
|krdS qW W n tk
r   dS X d
S )z
    Check if an objects needs to be rebuild based on its dependencies

    Parameters
    ----------
    obj : str
        object file

    Returns
    -------
    bool
    z.dTrN    c             S   s$   g | ]}|d kr|j d r|qS )
:)endswith).0x r   d/home/brian/BIRCH/lib-linux-x86_64/python/lib64/python3.6/site-packages/numpy/distutils/ccompiler.py
<listcomp>E   s    z _needs_build.<locals>.<listcomp>)posixFr#   )ospathexistsopen	readlinesr   joinshlexsplitstatst_mtimeOSError)objcc_argsextra_postargspp_optsdep_fileflinescmdlinelast_cmdlinecontentsdepst_objr   r   r    _needs_build%   s&    
r;   c                s:   t jd dk rtj d | }n fdd}t| || d S )Nr      c                s    | f||S )Nr   )selfargskw)funcr   r    <lambda>\   s    z replace_method.<locals>.<lambda>)sysversion_infotypes
MethodTypesetattr)klassmethod_namer@   mr   )r@   r    replace_methodW   s    rJ   c             C   s   dS )z
    Does nothing here, but is called by the get_version method and can be
    overridden by subclasses. In particular it is redefined in the `FCompiler`
    class where more documentation can be found.

    Nr   )r=   r   r   r    CCompiler_find_executablese   s    rK   find_executablesc             C   s   |dkr"|}t |r"djt|}tj| y&| jr@tj| ntj|tjd W nJ tj	k
r } z|j
}|j}W Y dd}~X n  tk
r   d}d}Y nX dS t |rdjt|}| jrt| tjd|rd}nd}td	|||f dS )
a  
    Execute a command in a sub-process.

    Parameters
    ----------
    cmd : str
        The command to execute.
    display : str or sequence of str, optional
        The text to add to the log file kept by `numpy.distutils`.
        If not given, `display` is equal to `cmd`.

    Returns
    -------
    None

    Raises
    ------
    DistutilsExecError
        If the command failed, i.e. the exit status was not 0.

    N )stderr       s   Too many open filesz2
Try rerunning setup command until build succeeds.r   z)Command "%s" failed with exit status %d%s)r   r)   listr   infoverbose
subprocesscheck_outputSTDOUTCalledProcessErroroutput
returncoder.   r   researchr   )r=   cmddisplayexcosmsgr   r   r    CCompiler_spawns   s2    

rb   spawnr   c             C   s   |dkrd}g }x|D ]}t jjt jj|\}}t jj|d }|t jj|d }|jdr|jdd }|d| }	t jjt jj	|	}	|	||d  }|| j
krtd||f |rt jj|}t jj||| j }
|j|
 qW |S )a  
    Return the name of the object files for the given source files.

    Parameters
    ----------
    source_filenames : list of str
        The list of paths to source files. Paths can be either relative or
        absolute, this is handled transparently.
    strip_dir : bool, optional
        Whether to strip the directory from the returned paths. If True,
        the file name prepended by `output_dir` is returned. Default is False.
    output_dir : str, optional
        If given, this path is prepended to the returned paths to the
        object files.

    Returns
    -------
    obj_names : list of str
        The list of paths to the object files corresponding to the source
        files in `source_filenames`.

    Nr   r   z..   z"unknown file type '%s' (from '%s'))r$   r%   splitextnormpath
splitdriveisabs
startswithrfindbasenameabspathsrc_extensionsUnknownFileErrorr)   obj_extensionappend)r=   source_filenames	strip_dir
output_dir	obj_namessrc_namebaseextidobj_namer   r   r    CCompiler_object_filenames   s&    


r{   object_filenamesc	                sr  t  }	t tdkrtj|	aW dQ R X |s0g S tjd dk rTddlm}
m	}m
} nddlm}
m	}m
} t|
rg }x<dD ]4}td	| }|dkrq||jd
|dj|f  q|W dj|}nj}ddj|f }tj| j|||||\}}}j|| ddj  }r2|ddj 7 }tj|  fdd}t|
rt|j }g g  }}x||D ]t}||krv|| \}}jdkrt|}t|}||r|| r|j|||ff n|j|||ff qvW |}x |D ]}|| qW n|j }t|dkrV|	dkrVddl}|jj|	}|j|| |j  nx|D ]}|| q\W |S )a  
    Compile one or more source files.

    Please refer to the Python distutils API reference for more details.

    Parameters
    ----------
    sources : list of str
        A list of filenames
    output_dir : str, optional
        Path to the output directory.
    macros : list of tuples
        A list of macro definitions.
    include_dirs : list of str, optional
        The directories to add to the default include file search path for
        this compilation only.
    debug : bool, optional
        Whether or not to output debug symbols in or alongside the object
        file(s).
    extra_preargs, extra_postargs : ?
        Extra pre- and post-arguments.
    depends : list of str, optional
        A list of file names that all targets depend on.

    Returns
    -------
    objects : list of str
        A list of object file names, one per source file `sources`.

    Raises
    ------
    CompileError
        If compilation fails.

    Nr   r<   r   )	FCompiler	is_f_filehas_f90_headerf77f90fix	compiler_zFortran %s compiler: %srM   r   zC compiler: %s
zcompile options: '%s'z
extra options: '%s'c                s   | \}\}}t | sd S x2t |tkr:tj| P W d Q R X tjd q W z(t j|||  W d Q R X W d t tj| W d Q R X X d S )Ng?)	r;   _global_lock_processing_filesaddtimesleep_job_semaphore_compileremove)r>   r/   srcrw   )r0   r1   r2   r=   r   r    single_compile3  s    
"z)CCompiler_compile.<locals>.single_compileabsoft)r   r   r   ) r   r   r   	threading	SemaphorerB   rC   	fcompilerr}   r~   r   numpy.distutils.fcompiler
isinstancegetattrrp   r)   compiler_sor   rR   _setup_compile_get_cc_argsrQ   keyscompiler_typer   itemslenmultiprocessing.poolpool
ThreadPoolmapclose)r=   sourcesrs   macrosinclude_dirsdebugextra_preargsr1   dependsjobsr}   r~   r   r]   fcfcompccompobjectsbuildr   objects_to_buildf77_objectsother_objectsr/   r   rw   build_itemsr_   multiprocessingr   r   )r0   r1   r2   r=   r    CCompiler_compile   sh    +









r   compilec                s   t jd| jj jjf   fdd}|dr<| j j |drdx jD ]\}}| j|| qLW |drx jD ]}| j	| qtW |dr| j
| j j  |dr| j| j j  |d	r| j j |d
r| j j dS )a  
    Customize compiler using distutils command.

    Parameters
    ----------
    cmd : class instance
        An instance inheriting from `distutils.cmd.Command`.
    ignore : sequence of str, optional
        List of `CCompiler` commands (without ``'set_'``) that should not be
        altered. Strings that are checked for are:
        ``('include_dirs', 'define', 'undef', 'libraries', 'library_dirs',
        'rpath', 'link_objects')``.

    Returns
    -------
    None

    zcustomize %s using %sc                s   t  | d d k	o| kS )N)r   )attr)r\   ignorer   r    allow  s    z&CCompiler_customize_cmd.<locals>.allowr   defineundef	librarieslibrary_dirsrpathlink_objectsN)r   rR   	__class____name__set_include_dirsr   r   define_macror   undefine_macroset_librariesr   set_library_dirsr   set_runtime_library_dirsr   set_link_objectsr   )r=   r\   r   r   namevaluemacror   )r\   r   r    CCompiler_customize_cmdv  s&    r   customize_cmdc          
      s   g }d}t | jj }xdD ]}||kr|j| qW x@|D ]8}t| |r<t| |}t|t|}|j|t|f q<W dt|d  d   fdd|D }dj	|S )Nr   versionr   r   object_switchcompile_switchr   r   r   r   r   z%-r   zs = %sc                s   g | ]} | qS r   r   )r   prop)fmtr   r    r!     s    z'_compiler_to_string.<locals>.<listcomp>r   )
r   r   r   r   r   r   r   r   r   r   )
rQ   executablesr   rp   hasattrr   maxr   reprr)   )compilerpropsmxr   keyvr5   r   )r   r    _compiler_to_string  s      


r   c             C   s`   y| j   W n tk
r    Y nX tjjdk r\tdd  t| j tt|  tdd  dS )z
    Print the compiler customizations to stdout.

    Parameters
    ----------
    None

    Returns
    -------
    None

    Notes
    -----
    Printing is only done if the distutils log threshold is < 2.

    rd   r   P   N)get_version	Exceptionr   _global_log	thresholdprintr   r   )r=   r   r   r    CCompiler_show_customization  s    
r   show_customizationc       
   "   C   s  t jd| jj  t|  |ry| jjd W n ttfk
rF   Y nX t	| drd| j
d kr| js| j
d jdrd\}}nd\}}| j
d j||g| j
d	d
  | _n8t	| drt jd| j
f  t	| dst jd| jj  t	| dr*d| j
d ks"d| j
d ks"d| j
d kr*d| _ntjdkrdd
l}dd
l}|j }zvyTtjj|d}t|d}	|	jd W d
Q R X | j|g|dd|d gd d| _W n tk
r   d| _Y nX W d
|j| X d
S )am  
    Do any platform-specific customization of a compiler instance.

    This method calls `distutils.sysconfig.customize_compiler` for
    platform-specific customization, as well as optionally remove a flag
    to suppress spurious warnings in case C++ code is being compiled.

    Parameters
    ----------
    dist : object
        This parameter is not used for anything.
    need_cxx : bool, optional
        Whether or not C++ has to be compiled. If so (True), the
        ``"-Wstrict-prototypes"`` option is removed to prevent spurious
        warnings. Default is False.

    Returns
    -------
    None

    Notes
    -----
    All the default options used by distutils can be extracted with::

      from distutils import sysconfig
      sysconfig.get_config_vars('CC', 'CXX', 'OPT', 'BASECFLAGS',
                                'CCSHARED', 'LDSHARED', 'SO')

    zcustomize %sz-Wstrict-prototypesr   ccr   gccg++c++r   Nz#### %s #######compiler_cxxzMissing compiler_cxx fix for clangTr"   zfile.cwzint a;
z-MMDz-MFz.d)rs   r   F)r   r   )r   r   )r   rR   r   r   r   r   r   AttributeError
ValueErrorr   r   r   ri   replacewarn_auto_dependsr$   r   tempfileshutilmkdtempr%   r)   r'   writer   r   rmtree)
r=   distneed_cxxabr   r   tmpdirfnr4   r   r   r    CCompiler_customize  sJ    




r   	customize[-.\d]+c                s    fdd}|S )aU  
    Simple matching of version numbers, for use in CCompiler and FCompiler.

    Parameters
    ----------
    pat : str, optional
        A regular expression matching version numbers.
        Default is ``r'[-.\d]+'``.
    ignore : str, optional
        A regular expression matching patterns to skip.
        Default is ``''``, in which case nothing is skipped.
    start : str, optional
        A regular expression matching the start of where to start looking
        for version numbers.
        Default is ``''``, in which case searching is started at the
        beginning of the version string given to `matcher`.

    Returns
    -------
    matcher : callable
        A function that is appropriate to use as the ``.version_match``
        attribute of a `CCompiler` class. `matcher` takes a single parameter,
        a version string.

    c                s~   |j dd}d}r0tj|}|s(d S |j }xBtj||d  }|sNd S  rntj |jdrn|j }q2P q2W |jdS )Nr   rM   r   )r   rZ   matchendr[   group)r=   version_stringposrI   )r   patstartr   r    matcherE  s     z%simple_version_match.<locals>.matcherr   )r  r   r  r  r   )r   r  r  r    simple_version_match+  s    r  Fc       	   &      s:  | rt | dr| jS | j  y
| j}W n tk
r<   dS X | sN|d  rRdS y
| j}W n@ tk
r   y
| j W n tk
r   dS X  fdd}Y nX ytj|tj	d}W nL tj
k
r } z|j}|j}W Y dd}~X n* tk
 r   d}d}Y nX t|}d}d}||kr0||}|r0t|}|| _|S )	a  
    Return compiler version, or None if compiler is not available.

    Parameters
    ----------
    force : bool, optional
        If True, force a new determination of the version, even if the
        compiler already has a version attribute. Default is False.
    ok_status : list of int, optional
        The list of status values returned by the version look-up process
        for which a version string is returned. If the status value is not
        in `ok_status`, None is returned. Default is ``[0]``.

    Returns
    -------
    version : str or None
        Version string, in the format of `distutils.version.LooseVersion`.

    r   Nr   c                s"   t j | }|sd S |jd}|S )Nr   )rZ   r   r   )r   rI   r   )r  r   r    r  ~  s
    
z&CCompiler_get_version.<locals>.matcher)rN   rP   rO   )r   r   rL   version_cmdr   version_matchversion_patternrT   rU   rV   rW   rX   rY   r.   r   r   )	r=   force	ok_statusr  r  rX   r^   statusr   r   )r  r    CCompiler_get_versionZ  sD    




r  r   c             C   s   | j d
kr| S t| }|jd g|jdd  |_tjjdrrd|jd krr|jd |jd g|jd	d  |_n|jd g|jdd  |_|S )z
    Return the C++ compiler.

    Parameters
    ----------
    None

    Returns
    -------
    cxx : class instance
        The C++ compiler, as a `CCompiler` instance.

    msvcintelwintelemwr   r   Naix	ld_so_aixrd   )r  r  r  )r   r   r   r   rB   platformri   	linker_so)r=   cxxr   r   r    CCompiler_cxx_compiler  s    
r  cxx_compilerintelccompilerIntelCCompiler(Intel C Compiler for 32-bit applicationsintelIntelItaniumCCompiler7Intel C Itanium Compiler for Itanium-based applicationsinteleIntelEM64TCCompiler(Intel C Compiler for 64-bit applicationsintelemIntelCCompilerW3Intel C Compiler for 32-bit applications on Windowsr  IntelEM64TCCompilerW3Intel C Compiler for 64-bit applications on Windowsr  pathccompilerPathScaleCCompiler2PathScale Compiler for SiCortex-based applicationspathcclinux.*ntwin32mingw32ccompilerMingw32CCompiler>Mingw32 port of GNU C Compiler for Win32(for MSC built Python)r   z+Setting mingw32 as default compiler for nt.c          "   C   sr  |d krt j t jk}| d kr$tj} y"|d kr6t| }t| \}}}W n8 tk
r~   d|  }|d k	rr|d|  }t|Y nX d| }yt	| W nv t
k
r
   tt }t jdt| |dd  }yt	| W n, t
k
r   tt }td| Y nX Y nX ytj| }	t|	| }
W n& tk
rL   td
||f Y nX |
d ||}||_t jd	|
  |S )Nz5don't know how to compile C/C++ code on platform '%s'z with '%s' compilerznumpy.distutils.z,%s in numpy.distutils; trying from distutils   z4can't compile C/C++ code: unable to load module '%s'z4can't compile C/C++ code: unable to find class '%s' zin module '%s'znew_compiler returns %szBcan't compile C/C++ code: unable to find class '%s' in module '%s')r   get_thresholdINFOr$   r   get_default_compilercompiler_classKeyErrorr
   
__import__ImportErrorstrr   rR   r	   rB   modulesvarsrS   r   )platr   rS   dry_runr  module_name
class_namelong_descriptionra   modulerG   r   r   r    new_compiler  sJ    



r?  c             C   sF   t | |||}g }x.|D ]&}t|r4|jt| q|j| qW |S )N)_distutils_gen_lib_optionsr   extendrQ   rp   )r   r   runtime_library_dirsr   r   lib_optsrx   r   r   r    gen_lib_options  s    
rD  msvc9r  _msvcbcppcygwincemxcunixcz
distutils.r   )N)r   r   )NNNr   NNN)r   )r   r   r   )r  r  r  )r  r  r  )r  r  r  )r  r   r!  )r  r"  r#  )r$  r%  r&  r(  r  r(  r  r(  r  r(  r'  r)  r  r)  r  )rK  rL  rM  rN  rO  rP  )r+  r,  r-  r)  r   )rQ  )NNNr   r   )rE  r  rF  rG  rH  rI  rJ  )H
__future__r   r   r   r$   rZ   rB   rD   r*   r   rT   r   	distutilsr   distutils.ccompilerdistutils.errorsr   r	   r
   r   distutils.sysconfigr   distutils.versionr   numpy.distutilsr   numpy.distutils.compatr   numpy.distutils.exec_commandr   r   numpy.distutils.misc_utilr   r   r   r   r   r   r5  dummy_threadingr   Lockr   setr   r;   rJ   rK   	CCompilerrb   r{   r   r   r   r   r   r  r  r  r2  _default_compilersr  rR   r?  _distutils_new_compilerrD  r@  _ccr7  get_mrF   r   r   r   r    <module>   s   2

?
-  
 )#
Q
/C           

    
(

