U
    |eA                     @   s  d dl Z d dlmZmZ d dlZd dlZd dlmZ d dlZ	d dl
Z
d dlmZmZmZmZmZ d dlmZ d dlmZ dd Zed	G d
d dejZe
je je
je je
je jiZe
je j e
j!e j"e
j#e j$e
j%e j&e
j'e j(e
j)e j*e
j+e j,e
j-e j.e
j/e j0e
j1e j2e
j3e j4e
j5e j6iZ7e
j8e j9e
j:e j;e
j<e j=e
j>e j?e
j@e jAe
jBe jCiZDdd ZEejFdd ZGG dd de jHZIe jJdddZKdd ZLdS )    N)defaultdictOrderedDict)SimpleNamespace)typestargetconfigirrewritescompiler)npydecl)DUFuncc                 C   s   t | tjtfS N)
isinstancenpufuncr   )func r   W/var/www/website-v5/atlas_env/lib/python3.8/site-packages/numba/np/ufunc/array_exprs.py	_is_ufunc   s    r   zafter-inferencec                       sh   e Zd ZdZ fddZdd Zdd Zdd	 Zd
d Zdd Z	dd Z
dd Zdd Zdd Z  ZS )RewriteArrayExprszThe RewriteArrayExprs class is responsible for finding array
    expressions in Numba intermediate representation code, and
    rewriting those expressions to a single operation that will expand
    into something similar to a ufunc call.
    c                    s4   t t| j|f|| |jj}d|kr0t|d< d S )N	arrayexpr)superr   __init__	targetctxspecial_ops_lower_array_expr)selfstateargskwsr   	__class__r   r   r      s    zRewriteArrayExprs.__init__c           	      C   s   t |dkrdS || _|| _t | _i | _|tj}|D ]X}|j	j
}|j}t|tjr|t||dtjr|| ||| q:t|tjr:|| j|< q:t | jdkS )z
        Using typing and a basic block, search the basic block for array
        expressions.
        Return True when one or more matches were found, False otherwise.
        r   FN)len
crnt_blocktypemapr   array_assignsconst_assigns
find_instsr   Assigntargetnamevaluer   Exprgetr   Array_match_array_exprConst)	r   func_irblockr#   	calltypesassignmentsinstrtarget_nameexprr   r   r   match!   s"    zRewriteArrayExprs.matchc                    s   |j } j}|dkrD|jtjkrDt fdd| D r|||< nR|dkr|jj j	kr j	|jj }t
|tjr|j}t|r ||s|||< dS )z
        Find whether the given assignment (*instr*) of an expression (*expr*)
        to variable *target_name* is an array expression.
        unarybinopc                 3   s   | ]} j |j jV  qd S r   )r#   r)   is_internal.0varr   r   r   	<genexpr>Q   s   z6RewriteArrayExprs._match_array_expr.<locals>.<genexpr>callN)opr$   fnr
   supported_array_operatorsall	list_varsr   r)   r#   r   r   Function
typing_keyr   _has_explicit_output)r   r4   r6   r5   Zexpr_opr$   	func_typefunc_keyr   r?   r   r.   B   s     

z#RewriteArrayExprs._match_array_exprc                 C   s,   t |jt |j }|jdk	r"dS ||jkS )zr
        Return whether the *expr* call to *func* (a ufunc) features an
        explicit output argument.
        NT)r!   r   r   varargnin)r   r6   r   nargsr   r   r   rI   `   s    
z&RewriteArrayExprs._has_explicit_outputc                 C   s>   |j }|dkr|jS |dkr,| j|jj jS td|d S )Nr8   rA   z:Don't know how to find the operator for '{0}' expressions.)rB   rC   r#   r   r)   rH   NotImplementedErrorformatr   ir_exprir_opr   r   r   _get_array_operatorl   s    z%RewriteArrayExprs._get_array_operatorc                 C   sJ   |j }|dkr|j|jfS |dkr*| S |dkr8|jS td|dS )z{Given a Numba IR expression, return the operands to the expression
        in order they appear in the expression.
        r:   r9   rA   z:Don't know how to find the operands for '{0}' expressions.N)rB   lhsrhsrF   r   rO   rP   rQ   r   r   r   _get_operandsv   s    zRewriteArrayExprs._get_operandsc                    s:   |j }|dkr|jS  fdd |D } ||fS )zZTranslate the given expression from Numba IR to an array expression
        tree.
        r   c                    s   g | ]} j |j|qS r   )r%   r,   r)   )r=   Zop_varr?   r   r   
<listcomp>   s   z5RewriteArrayExprs._translate_expr.<locals>.<listcomp>)rB   r6   rW   rT   )r   rR   rS   Zoperands_or_argsr   r?   r   _translate_expr   s    
z!RewriteArrayExprs._translate_exprc                 C   sV  i }t  }tt}| j D ],}|j}g }| ||f}tjd|j	|| j
|jj d}t||j|j	}	|	||< |	| j|jj< | |D ]}
|
j}|
jr|| jkr| j| }|j}| }|D ]}
||
j  d7  < q|| | |jjrH||jj d||< q|| jkr,|| j|  q||
j  d7  < ||
 qq|||fS )ztIterate over the matches, trying to find which instructions should
        be rewritten, deleted, or moved.
        r   )rB   locr6   ty   N)setr   intr$   valuesr*   rT   r   r+   rZ   r#   r(   r)   r'   rW   is_temprF   appendrY   addr%   )r   replace_map	dead_vars	used_varsr4   r6   Zarr_inpsZarr_exprnew_expr	new_instroperandZoperand_nameZchild_assignZ
child_exprZchild_operandsr   r   r   _handle_matches   s@    


z!RewriteArrayExprs._handle_matchesc                 C   s   || }||kr|| }q|S )zFind the final replacement instruction for a given initial
        instruction by chasing instructions in a map from instructions
        to replacement instructions.
        r   )r   Zreplacement_mapr4   replacementr   r   r   _get_final_replacement   s    
z(RewriteArrayExprs._get_final_replacementc                 C   s6  |   \}}}| j }|  i }| jjD ]}t|tjr||kr| ||}|r|	| |j
 D ]>}|j}	|	|kr|	||	 ||	 dkrh||	  d8  < qhn
|	| q,t|tjr|j
}
||
 dkr||
  d8  < |||
< n|
|kr|	| q,|	| q,|r2| D ]}|| q |S )z}When we've found array expressions in a basic block, rewrite that
        block, returning a new, transformed block.
        r   r\   )ri   r"   copyclearbodyr   r   r'   rk   ra   r*   rF   r)   popDelr_   insert_before_terminator)r   rc   rd   re   resultZ
delete_mapr4   rj   r>   var_nameZinstr_valuer   r   r   apply   s@    
 


zRewriteArrayExprs.apply)__name__
__module____qualname____doc__r   r7   r.   rI   rT   rW   rY   ri   rk   rt   __classcell__r   r   r   r   r      s   !
%
r   c                 C   s  t | tr.| \}}g }i }|D ]$}t|\}}|| || q |tjkrt|dkr|tkrt	
|d t|  |d |fS |tkrt	|d t|  g|d g|fS n&|tkstt	t|  |d |fS nRt|rdtt|dd}t	|t	 }	|||< t	|	|g }
|
|fS n^t | tjrnt	j| jt	 | jj| jjrb| jjnddi fS t | tjrt	| j i fS t!d| f d	S )
z[Build a Python expression AST from an array expression built by
    RewriteArrayExprs.
       r   r\   z__ufunc_or_dufunc_{0}-_)lineno
col_offsetz1Don't know how to translate array expression '%r'N)"r   tuple_arr_expr_to_astra   updater
   rD   r!   _binopsastBinOp_cmpopsCompare	_unaryopsAssertionErrorUnaryOpr   rP   hexhashreplaceNameLoadCallr   Varr)   rZ   linecolr/   Numr*   rO   )r6   rB   arr_expr_argsast_argsenvargZast_argZ	child_envfn_nameZfn_ast_nameZast_callr   r   r   r   
  s`    

   
 

r   c              	   c   s   t  }| D ]Z}|j}|jj||jdj}|dddd}||krRt|d||f||< ||_q
t|}z
|V  W 5 | D ]\}}||_qX dS )za
    Legalize names in the variable list for use as a Python function's
    parameter names.
    )rZ   $r|   .z not uniqueN)	r   r)   scoperedefinerZ   r   r   listr_   )Zvar_listvar_mapr>   old_namenew_nameparam_namesr   r   r   _legalize_parameter_names2  s    
r   c                       s(   e Zd Zejejd fddZ  ZS )_EraseInvalidLineRanges)nodereturnc                    s>   t  |}t|dr:t|dd d k	r:|j|jkr:|`|`|S )Nr}   
end_lineno)r   generic_visithasattrgetattrr}   r   )r   r   r   r   r   r   M  s    
z%_EraseInvalidLineRanges.generic_visit)ru   rv   rw   r   ASTr   ry   r   r   r   r   r   L  s   r   Zastreec                 C   s$   t |  t |  t |  dS )z)Inplace fixes invalid lineno ranges.
    N)r   fix_missing_locationsr   visitr   r   r   r   _fix_invalid_lineno_rangesW  s    
r   c              	      s  dt t|dd }|jj}| }tt|dd d}dd |D }t|t}d	d |D }t	
d
||d}	t|	drt|	jdkst|	jd }
||
j_t|j\|
jd _}t|	 W 5 Q R X t|	|d}t|| || }j}j |jfdd|D  }g }|jD ]@}t|tjr0|j}t|tjrL||j  n
|| q|j!j | t"# $ }|dkrt%& n|' }d|_(|j) ||ddddl*m+} G  fddd|j,}t-t|d|d}|j.|j/ |_0fdd|D }|1| ||||S )z:Lower an array expression built by RewriteArrayExprs.
    z__numba_array_expr_%sr{   r|   c                 S   s   | j S r   r)   )r>   r   r   r   <lambda>j      z#_lower_array_expr.<locals>.<lambda>)keyc                 S   s   g | ]
}|j qS r   r   r<   r   r   r   rX   m  s     z%_lower_array_expr.<locals>.<listcomp>c                 S   s   g | ]}t |d qS r   )r   r   )r=   
param_namer   r   r   rX   q  s   zdef {0}(): returnexecrn   r\   r   c                 3   s   | ]}  |V  qd S r   )typeofr=   r)   lowererr   r   r@     s     z$_lower_array_expr.<locals>.<genexpr>NnumpyF)flagscaching)npyimplc                       s   e Zd Z fddZdS )z%_lower_array_expr.<locals>.ExprKernelc                    sL   t | jjj} fdd|D } jj|} |j jjS )Nc                    s    g | ]\}}}  |||qS r   )cast)r=   valintyouttyr?   r   r   rX     s   zB_lower_array_expr.<locals>.ExprKernel.generate.<locals>.<listcomp>)zip	outer_sigr   contextcall_internalfndescr   return_type)r   r   Zarg_zip	cast_argsrr   buildercres	inner_sigr?   r   generate  s    
   
z._lower_array_expr.<locals>.ExprKernel.generateN)ru   rv   rw   r   r   r   r   r   
ExprKernel  s   r   )rM   noutru   c                    s   g | ]}  |qS r   )loadvarr   r   r   r   rX     s     )2r   r   r   rZ   filenamerF   sortedr]   r   r   parserP   r   r!   rn   r   r   r   r6   r*   r   compiler   r   r   r[   r   r   Optionaltyper-   ra   dtyper   r   ConfigStacktop_or_noner	   Flagsrl   error_modelcompile_subroutinenumba.npr   _Kernelr   rM   r   rN   numpy_ufunc_kernel)r   r6   Z	expr_nameZexpr_filenameZexpr_var_listZexpr_var_unique	expr_argsZexpr_paramsr   Z
ast_moduleZast_fn	namespacecode_objimplr   r   Zinner_sig_argsargtyr   r   r   r   r   r   )r   r   r   r   r   r   b  sf    
 


     r   )Mr   collectionsr   r   
contextlibsysr   r   r   r   operator
numba.corer   r   r   r	   numba.core.typingr
   Znumba.np.ufunc.dufuncr   r   register_rewriteRewriter   posUAddnegUSubinvertInvertr   rb   AddsubSubmulMulttruedivDivmodModor_BitOrrshiftRShiftxorBitXorlshiftLShiftand_BitAndpowPowfloordivFloorDivr   eqEqneNotEqltLtleLtEgtGtgeGtEr   r   contextmanagerr   NodeTransformerr   r   r   r   r   r   r   r   <module>   s    X                     
(
