U
    9%eDE                    @   sh  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Zd dl	Z
d dlZd dlmZ d dlmZmZmZmZmZmZ d dlmZmZmZmZmZmZmZmZmZmZmZm Z m!Z!m"Z"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-m.Z.m/Z/m0Z0 d d
l1m2Z2 G dd de)j3Z4dd Z5dd Z6edddddddgddZ7dd Z8G dd de0Z9dd Z:d d! Z;d"d# Z<d$d% Z=d&d' Z>d(d) Z?d*d+ Z@d,d- ZAd.d/ ZBd0d1 ZCd2d3 ZDd4d5 ZEd6d7 ZFd8d9 ZGd:d; ZHd<d= ZId>d? ZJd@dA ZKdBdC ZLdDdE ZMdFdG ZNdHdI ZOdJdK ZPdLdM ZQdNdO ZRdPdQ ZSdRdS ZTdTdU ZUdVdW ZVdXdY ZWdZd[ ZXd\d] ZYdS )^    N)make_dataclass)parfor)typesirconfigcompilersigutilscgutils)add_offset_to_labelsreplace_var_namesremove_delslegalize_namesrename_labelsget_name_var_tablevisit_vars_innerget_definitionguardget_call_tableis_pureget_np_ufunc_typget_unused_var_nameis_const_callfixup_var_define_in_scopetransfer_scopefind_max_labelget_global_func_typ)	signature)lowering)ensure_parallel_support)NumbaParallelSafetyWarningNotDefinedErrorCompilerErrorInternalError)ParforLoweringBuilderc                       s    e Zd ZdZ fddZ  ZS )ParforLowerzlThis is a custom lowering class that extends standard lowering so as
    to accommodate parfor.Parfor nodes.c                    s(   t |tjrt| | nt | d S N)
isinstancer   Parfor_lower_parfor_parallelsuper
lower_instselfinst	__class__ \/var/www/html/Darija-Ai-API/env/lib/python3.8/site-packages/numba/parfors/parfor_lowering.pyr*   1   s    zParforLower.lower_inst)__name__
__module____qualname____doc__r*   __classcell__r0   r0   r.   r1   r$   ,   s   r$   c                 C   s$   |j d krt| |S | | |S d S r%   )lowerer_lower_parfor_parallel_std)r7   r   r0   r0   r1   r(   8   s    

r(   c           F      C   s  ddl m} t  | jj}| j}| j}| jj}t|| j_t	j
rVtd| jt| j | jj}| j}t	j
rztd |  |jj}	|jj}
t	j
rtd|jdt|j |jjD ]}t	j
rtd| | | q|jD ]0}||kr|| }t|
||	}| |j| qi }i }tjj||j|| j|| t	j
rFtd| td	| |jd
k	sVttjj ||j}|j!|j" }}t	j
rtd| td| t#|}i }g }|dkrP|jj}
|jj}	t$| |
|	d}|j%tj&j'j(j)t*tj&j'j(j)dd}|j+|j,|g dt-j.dd}t/|D ]:}|| }| jj| }t|
||	}t0|}|j1}t	j
rptd||||t-2||t| t3|t-j4j5r|j6d } nd} |j%t&j7t8t&j7t-9t-j.| fdt-2|id}!|g}"t3|t-j4j5r:|j+tj:;|d|	t-9t-j.|j6dd}#t/|j6D ]0}$|j+tj:<|#|$d
|	t-j.dd}%|"=|% q|j>|"dd}&|j?@|}'|jA|'t-2|d}(|j,|!|&|(gd})|j+|)|dd}*|*||j< |=|* || jB}+|+d
k	rHt3|t-j4j5r6|j%t&jCt8t&jCt-9t-j.|j6|fdt-2|id},|jA|+|dd}-|j,|,|#|-|(gd}.|j+|.|d d}/|=|/ n|jA|+|d d}/n|}/t	jDrd!tE| d" }0t-F|0}1|jA|0|1d#d}2tjG|2|gd
|	d$}3tHt-jI||2j ||j | jjJ|3< td%|3 | |3 ||j }4|K|4}5tLM||5}6|
Nd&|	}7|4||7j< |6| j|7j< tLjO|| P|j|5d'$}8|Q|8jR|6 |jS|*|7|/d( W 5 Q R X q|jT }9d)|9_U||jVd jWj }:|jVdd
 D ]};||;jWj |:kstqd*tjj_Xz.tY| |||||9i tZ||:|j
\}<}=}>}?}@W 5 d+tjj_XX d,g|= }=t#|}At#|=t#| |A }Bt	j
rDtd-|= td.|B td/| td0| td1|A t[|j\|B|A|=|>|j|}Ct	j
rntd2|C d3d4 |jVD }Dt	j
rtd5|jV td6|D t]| |<|C|>|=|?|D||||j|:|j|@ |dkrt^||| || |D ]}E| tj_|Ej|	d7 q|| j_t	j
rtd8 d
S )9a  Lowerer that handles LLVM code generation for parfor.
    This function lowers a parfor IR node to LLVM.
    The general approach is as follows:
    1) The code from the parfor's init block is lowered normally
       in the context of the current function.
    2) The body of the parfor is transformed into a gufunc function.
    3) Code is inserted into the main function that calls do_scheduling
       to divide the iteration space for each thread, allocates
       reduction arrays, calls the gufunc function, and then invokes
       the reduction function across the reduction arrays to produce
       the final reduction values.
    r   )get_thread_countzlowerer.fndescr(   zinit_block =  zlower init_block instr = 	alias_maparg_aliasesNzparfor_redvars:zparfor_reddict:)r7   scopelocr0   )fobjftypeargs)rA   num_threads_var)rhstypnameZreduction_info   dtype)r?   r@   rA   kwsshapeZredarr_shapeZredshapeonedimZtuple_size_varrE   )cvalrD   redarrinit_val)rK   rD   rE   redtosetzres_print1 for redvar :	str_constrA   varargr>   Zres_print_redvarz$loop_index)intp)objindexvalnumpyTFschedzfunc_args = znum_inputs = parfor_outputs = parfor_redvars = znum_reductions = zgu_signature = c                 S   s   g | ]}|j |j|jfqS r0   )startstopstep.0lr0   r0   r1   
<listcomp>p  s     z._lower_parfor_parallel_std.<locals>.<listcomp>zloop_nests = loop_ranges = )r>   z_lower_parfor_parallel done)`numba.np.ufunc.parallelr9   r   contextZtyping_contextbuilderfndesctypemapcopyr   DEBUG_ARRAY_OPTprinttypevarmapdump
init_blockr>   r=   bodyr*   racesr   VarZ_alloca_varrE   numbaparforsr   Zfind_potential_aliases_parforparamsfunc_irAssertionErrorget_parfor_outputsredvarsreddictlenr#   Zbind_global_functionnpZufuncparallelZ_iget_num_threadsr   Zassigncallr   rS   rangeredtyp_to_redarraytyperG   ZDTyper&   npytypesArrayndimemptyr   UniTupleExprgetattrZstatic_getitemappendZmake_tuple_variableZ
_typingctxZresolve_value_typeZmake_const_variablerM   fullDEBUG_ARRAY_OPT_RUNTIMEstrStringLiteralPrintr   none	calltypesget_value_typer	   alloca_onceredefine	for_rangeloadvarstorerU   setitemflagsZerror_model
loop_nestsindex_variableZsequential_parfor_lowering_create_gufunc_for_parfor_bodybool_create_shape_signatureget_shape_classescall_parallel_gufunc#_parfor_lowering_finalize_reductionDel)Fr7   r   r9   	typingctx	targetctxre   Zorig_typemaprg   rl   r>   r=   instrZracevarZrvtyprvr;   r<   Zparfor_output_arraysparfor_redvarsparfor_reddictnredvarsredarrsZ
to_cleanupZpfbdrget_num_threadsrB   iZred_name
redvar_typZredvarZredarrvar_typZreddtype	redarrdimZglbl_np_emptyZsize_var_listZredshape_varjZ	onedimvarZsize_varrK   dtZ
empty_call
redarr_varrM   Zfull_func_nodeZinit_val_varZ	full_callrN   Zres_print_strstrconsttyplhs	res_printZnum_thread_typeZntllvm_typeZalloc_loop_varZnumba_ir_loop_index_varloopr   index_var_typr`   funcZ	func_argsfunc_sigfunc_arg_typesexp_name_to_tuple_varnum_reductions
num_inputsgu_signatureloop_rangesvr0   r0   r1   r8   ?   s    

  

 



	   



 

 






        








    r8   _ReductionInforedvar_inforedvar_namer   r   
redarr_typrM   T)frozenc              	   C   st   |  D ]f\}}|jj| }|jj|j }||}	t|| |||||	d}
|
jjdk	r\tnt	}|| |||
 qdS )zYEmit code to finalize the reduction from the intermediate values of
    each thread.
    )r   r   r   r   r   rM   N)
itemsrf   rg   rE   r   r   r   Zredop_lower_trivial_inplace_binops_lower_non_trivial_reduce)r   r   r7   r   thread_count_varr   r   r   r   rM   reduce_infohandlerr0   r0   r1   r     s"    


r   c                       s   e Zd Z fddZ  ZS ) ParforsUnexpectedReduceNodeErrorc                    s   t  d|  d S )Nz!Unknown reduce instruction node: )r)   __init__r+   r.   r0   r1   r     s    z)ParforsUnexpectedReduceNodeError.__init__)r2   r3   r4   r   r6   r0   r0   r.   r1   r     s   r   c                 C   s   |j jD ]b}t||rn>t||jrN|jj}t||||}|j||j	j
d nt|t| |||jr qlqtjr|j}|| j d|j d| d| dS )z+Lower trivial inplace-binop reduction.
    rJ   z	: parfor z reduction  =N)r   reduce_nodes_lower_var_to_var_assign!_is_inplace_binop_and_rhs_is_initr   valuefn_emit_binop_reduce_callstorevartargetrE   r   _fix_redvar_name_ssa_mismatchr   r   print_variabler>   r2   )r   r7   r   r   r-   r   redvar_resultvarnamer0   r0   r1   r     s.    
   r   c           
   	      s   |j  d |jj |j ||j}t|j	|}|j
}|jjD ]v}t||rXnRt|tjrt fdd| D rt|||}||  || nt|t| |||j rH qqHW 5 Q R X tjr|j }	|| j d|	 d|	 dS )zFLower non-trivial reduction such as call to `functools.reduce()`.
    #initc                 3   s   | ]}|j  kV  qd S r%   rJ   r_   varZ	init_namer0   r1   	<genexpr>  s     z,_lower_non_trivial_reduce.<locals>.<genexpr>z: parfor non-trivial reduction r   N)r   rf   rg   
setdefaultr   r   rE   r	   r   re   rU   r   r   r   r&   r   AssignanyZ	list_vars_emit_getitem_callr   r*   r   r   r   r   r   r>   )
r   r7   r   r   Znum_thread_llvalr   tidr-   elemr   r0   r   r1   r     s2    
r   c                 C   sB   t |tjr>t |jtjr>| |jj}| j||jjd dS dS )zaLower Var->Var assignment.

    Returns True if-and-only-if `inst` is a Var->Var assignment.
    rJ   TF)	r&   r   r   r   rq   r   rE   r   r   )r7   r-   Zloadedr0   r0   r1   r     s
    r   c                 C   sT   dd }|j }|j}|j}||jj}|| f}t|j|tj	}	|
|||	|}
|
S )z%Emit call to ``redarr_var[idx]``
    c                 S   s   | | S r%   r0   )rL   rU   r0   r0   r1   reducer_getitem  s    z+_emit_getitem_call.<locals>.reducer_getitem)re   rd   r   r   r   rE   r   r   r   rS   compile_internal)idxr7   r   r   re   ctxr   arg_arrrA   sigr   r0   r0   r1   r     s    r   c              
   C   s   dd }dd }t j|t j|t j|t j|t j|i|  }|j}|j}|j}	|	|j
j}
tjr|j
j|j}tj|j
|gd|jd}|jj}ttj||j
j ||j |jj|< || |	|j}||
|jf}t|jtj|	|j}|||||}|S )z;Emit call to the ``binop`` for the reduction variable.
    c                 S   s"   |}t | D ]}||| 7 }q|S r%   r~   Zthread_countrL   initcr   r0   r0   r1   reduction_add.  s    z._emit_binop_reduce_call.<locals>.reduction_addc                 S   s"   |}t | D ]}||| 9 }q|S r%   r   r   r0   r0   r1   reduction_mul4  s    z._emit_binop_reduce_call.<locals>.reduction_mulNrQ   )operatoriaddisubimul	ifloordivitruedivrd   re   r   r   r   rE   r   r   r=   getr   r   r   r>   rf   rg   r   r   r   r   r*   rM   r   uintpr   )Zbinopr7   r   r   r   r   Zkernelr   re   r   r   Zinit_varr   rg   Zarg_thread_countrA   r   r   r0   r0   r1   r   *  sV           

   r   c                 C   sN   t | tjsdS | j}t |tjs&dS |jdkr4dS |jj| dkrJdS dS )zDIs ``inst`` an inplace-binop and the RHS is the reduction init?
    FZinplace_binopr   T)r&   r   r   r   r   oprC   rE   )r-   r   rC   r0   r0   r1   r   ^  s    
r   c           
      C   s   | j j}t|tjrz||}W n  tk
rB   ||jjk}Y nX |j	}|jj	}||k}|r||jjkr|
|jj}	|j|	|d dS dS )z5Fix reduction variable name mismatch due to SSA.
    rJ   TF)rn   r=   r&   r   r   Z	get_exactr    r   rE   Zunversioned_namer   r   )
r   r7   r-   r   r=   Zreduction_varZis_same_source_varZredvar_unver_nameZtarget_unver_namerV   r0   r0   r1   r   m  s    r   c              	      s  t jrBtd||| |dd D ]}td|t||d q"t|| }fdd|dd D }	t }
|	D ]}|rv|D ]}|
| qqv|
rt|
d nd}|	d|f |
| |d }|
| i t	d	}|
D ] }|dkrt
||< |d7 }qt
|}d
|i  fddg }g }d}d}t jrVtd| td|	 td| t|	|D ]t\}}|d }|rtfdd|D }nd}||kr|t|gt|dd   n|| ||7 }q`||fS )z&Create shape signature for GUFunc
    r   rF   Nargumentrg   c                    s$   g | ]}|kr |d ndqS )r   )r0   r   )r   rp   rg   r0   r1   ra     s     z+_create_shape_signature.<locals>.<listcomp>r   alatest_alphac                    s0   | dkr||  S  d  d7  < t  d S d S )Nr   r   rF   )chr)r   	class_map)
alpha_dictr0   r1   
bump_alpha  s    z+_create_shape_signature.<locals>.bump_alphar0   rA   classesthreadcount_ordinalc                 3   s   | ]} |V  qd S r%   r0   )r_   r   )r   r   r0   r1   r     s     z*_create_shape_signature.<locals>.<genexpr>)r   ri   rj   rk   rz   setaddmaxinsertordr   ziptupler   list)r   r   r   rA   r   rp   rg   r   Z
num_inoutsr   Z	class_set_classZ	max_classZthread_num_classalphabetnr  Zgu_sinZgu_soutcountZsyms_sinclsargZdim_symsr0   )r   r   r   r   rp   rg   r1   r     sV    







"
r   c                 C   s&   t | jD ]\}}td|d| q
d S )N    r:   )	enumeratero   rj   )blockr   r-   r0   r0   r1   _print_block  s    r  c                 C   s(   |   D ]\}}td| t| qdS )z%Pretty-print a set of IR blocks.
    zlabel: N)r   rj   r  )Z	body_dictlabelr  r0   r0   r1   _print_body  s    
r  c                 C   sF   |   }t| }t| }|| j}|| jt|| |S r%   )	rh   minkeysr  r>   ro   r   r   Jump)	loop_bodyblocksZfirst_label
last_labelr>   r0   r0   r1   wrap_loop_body  s    
r  c                 C   s(   t |  }| | jd d | | _d S )Nr   )r  r  ro   )r  r  r0   r0   r1   unwrap_loop_body  s    r  c                 C   s6   | |kr
n(| |kr(| |  ||  n
| |  dS )a_  If the variable is already defined more than once, do nothing.
       Else if defined exactly once previously then transition this
       variable to the defined more than once set (remove it from
       def_once set and add to def_more set).
       Else this must be the first time we've seen this variable defined
       so add to def_once set.
    N)r  remove)a_defdef_oncedef_morer0   r0   r1   add_to_def_once_sets  s    
r"  c                 C   sP  |  tj}|D ]8}|jj}t||| |j}	t|	tjrVt|	jt	j
rV|	jj||< t|	tjr|	jdkr|	jj|kr|	jj|	jf||< t|	tjr|	jdkr|	jj|kr||	jj \}
}|
|kr||
 }t||st|
|| nt|
|| t|	tjr|	jdkr|	jD ]<}t|tjr$|j}|| }t|ddrt||| qqdS )a  Effect changes to the set of variables defined once or more than once
       for a single block.
       block - the block to process
       def_once - set of variable names known to be defined exactly once
       def_more - set of variable names known to be defined more than once
       getattr_taken - dict mapping variable name to tuple of object and attribute taken
       module_assigns - dict mapping variable name to the Global that they came from
    r   r}   mutableFN)Z
find_instsr   r   r   rE   r"  r   r&   Globalpytypes
ModuleTyper2   r   r   attrr   r   rA   rq   r   )r  r   r!  getattr_takenrg   module_assignsZassignmentsZ
one_assignr  rC   Zbase_objZ	base_attrZbase_mod_nameZargvarZavtyper0   r0   r1   compute_def_once_block  s0    

""

r*  c           	   	   C   sh   |   D ]Z\}}t|||||| |jD ]8}t|tjr(t|j||||| t|j||||| q(qdS )zCompute the set of variables defined exactly once in the given set of blocks
       and use the given sets for storing which variables are defined once, more than
       once and which have had a getattr call on them.
    N)	r   r*  ro   r&   r   r'   rn   compute_def_once_internalr  )	r  r   r!  r(  rg   r)  r  r  r-   r0   r0   r1   r+  ;  s    
r+  c                 C   s.   t  }t  }i }i }t| ||||| ||fS )zRCompute the set of variables defined exactly once in the given set of blocks.
    )r  r+  )r  rg   r   r!  r(  r)  r0   r0   r1   compute_def_onceM  s    r,  c                 C   s    t | tjst|| j | S r%   )r&   r   rq   rv   r  rE   )r   Zvarsetr0   r0   r1   	find_varsW  s    r-  c           	      C   s8  | j j|kr4|| df tjdkr0td| d dS t }t| jt	| |
|}tjdkrntd| d|d| t|d	krt| jd |rtjdkrtd
| || j j  ||  t|| j j tjjs|| j jg7 }dS t|d	kr|| df tjdkr4td| d n&|| df tjdkr4td| d dS )Nzstored arrayrF   Instructionz: could not be hoisted because the created array is stored.Fz_hoist_internal:zuses:zdiff:r   zWill hoist instructionT
dependencyz. could not be hoisted because of a dependency.znot purez, could not be hoisted because it isn't pure.)r   rE   r   r   ri   rj   r  r   r   r-  
differencerz   r   r&   r   r   r   )	r-   dep_on_param
call_tablehoistednot_hoistedrg   stored_arraysZusesdiffr0   r0   r1   _hoist_internal\  s2    




r7  c                 C   s   |j D ]t}t|tjtjfrN| |jj t||j	j ddrz||j	j qt|t
jrt| ||j| t| ||j| qd S )Nr#  F)ro   r&   r   ZStaticSetItemSetItemr  r   rE   r   r   r   r'   find_setitems_blockrn   find_setitems_bodyr  )setitemsitemssetr  rg   r-   r0   r0   r1   r9  {  s    
r9  c                 C   s$   |  D ]\}}t| ||| qdS )z
      Find the arrays that are written into (goes into setitems) and the
      mutable objects (mostly arrays) that are written into other arrays
      (goes into itemsset).
    N)r   r9  )r;  r<  r  rg   r  r  r0   r0   r1   r:    s    r:  c                 C   sf   t | tjrbt | jtjrb| jjdkrb| jjj|krb|| jjj }|dtgkrbt	| ||||||S dS )Nr}   r   F)
r&   r   r   r   r   r   r   rE   r{   r7  )r-   r1  r2  r3  r4  rg   r5  	call_listr0   r0   r1   empty_container_allocator_hoist  s    

  r>  c                 C   s  t  | }g }g }t||\}}t|\}	}
t }t }t|||| tt||}tjdkr|t	d|d|d|d|d| 
 |D ]}t
||| q| D ]\}}g }|jD ]}t|||	||||rqnt|tjr|jj|krt|||	||||rqnt|tjrg }tjdkr(t	d |  |jjD ]b}t|||	||||rPq0n6t|tjr|jj|krt|||	||||rq0|| q0||j_|| q||_q||fS )NrF   zhoist - def_once:z	setitems:z	itemsset:zdep_on_param:zparfor_params:r   )rh   r,  r   r  r:  r	  r0  r   ri   rj   r"  r   ro   r>  r&   r   r   r   rE   r7  r   r'   rm   rn   r   )parfor_paramsr  rg   wrapped_blocksr1  r3  r4  r   r!  r2  Zreverse_call_tabler;  r<  sir  r  	new_blockr-   Znew_init_blockZib_instr0   r0   r1   hoist  sx    


          
   rC  c                 C   s   t | tjj S r%   )r&   r   r   r   )Zredtyper0   r0   r1   redtyp_is_scalar  s    rD  c                 C   s2   d}t | tjjr"|| j7 }| j} tj| |dS )ziGo from a reducation variable type to a reduction array type used to hold
       per-worker results.
    rF   C)r&   r   r   r   r   rG   )Zredtypr   r0   r0   r1   r     s
    
r   c                 C   s(   t | tjjsttj| j| j| jS )zYGiven a reduction array type, find the type of the reduction argument to the gufunc.
    )r&   r   r   r   rv   rG   r   Zlayout)Zredarraytypr0   r0   r1   redarraytype_to_sig  s    rF  c                 C   s2   t | }| D ]\}}||kr|| ||< q|S )aQ   We use ir_utils.legalize_names to replace internal IR variable names
        containing illegal characters (e.g. period) with a legal character
        (underscore) so as to create legal variable names.
        The original variable names are in the typemap so we also
        need to add the legalized name to the typemap as well.
    )r   r   )namesrg   Zoutdictxyr0   r0   r1   legalize_names_with_typemap  s
    rJ  c                 C   s    t | tjr| jdkr| jS | S )Nr   )r&   r   ArrayCompatibler   rG   )rH  r0   r0   r1   to_scalar_from_0d  s    
rL  c
           e   
      s  t jdkrtd |jj}
t|j}t| t|j	}dd |j	D }|j
}tjj||}| jjtjj| j||| jj\}}ttt|t| t| }t jdkrtd|dt| td|dt| td|dt| td	|dt| g }i }i }d
}g }|D ]T}| }t|tjs8t|tjr|j}|j}|t jksTtg }t |D ]B}dt!| }|"| |"| ||f||< |d7 }||< q`|||< |"| nt|tj#st|tj$rX|j}|j}|t jkstg }t |D ]F}dt!| }|"| |"| ||f||< |d7 }|| |< q|||< |"| n
|"| q|}t jdkrtd|dt| |	%t|}	|	D ]} d|  }!t&'t(|!|
 qt)|	|| jj g }"g }#|D ]\}$|$d }%|""|% t*|$ }&|#"|& t+|&}'|%kr*|% |'ks2tn|'|%< q|| |" }t jdkrtd|dt| td|dt| td|dt| t,| t-|| | t jdkrtdt. dt t-|  fdd|D }(t jdkrHtdt . dt  td|(dt|( |D ]*})td|) td|) dt|)  qfdd|D }*fdd|| D |# }+t jdkrtd|* td|+ t/| |},fdd|D }|}-g }d}.t t|-D ]P}/|.r|/t|k rt|*|/ tj0j1r|"|-|/ d  n|"|-|/  qt/|  t2|}0t3d|0}1t jdkrXtd|dt| d t4t5|6d!d" }2t jrtd#t|2d|2 d$}3|3d%|2 d& d'7| d( 7 }3t8td)}4|. D ]<\}5}6|5 }7|3d*|5  7 }3t|7tj$st|7tjrd+}8nd}8|8rt9t:| j|5}9d,}:t jr6td-|9t|9 |9d,k	rt|9t;j<r|9j=d.krt9t:| j|9j>}:t jrtd/|:t|: n4t|9t;j?r|9j@ }:t jrtd/|:t|:|:j@ |:d,k	rRt|:t;jAst|:t;jBr|:jC};t jrtd0|;t|; |;|4|:j@< nHt|:tjDjErv|:j@Fd1d
 }<t jrFtd2|<|:jGt|:jG |:jG|4|<< n$t jrbtd3 tHd4t!|5 |5j|3d5|7jGjI d1 7 }3tJ|6|7jKD ]"\}=}>|3|>d6 |=  d7 7 }3qn6|3d8d'7fd9d|6D  7 }3t|6dkr|3d77 }3|3d:7 }3qt t|D ]@}/|.r
t|*|/ tj0j1r
|3d*|-|/  d; ||/  d: 7 }3q
d<}?t|"d
krv|3d*|? d5 7 }3|3d=7 }3tJ|"|D ]\}%}$|3d*|$  d6 |%  d> |? d? 7 }3t jLr|3d@7 }3|3dA|$  d7 |$  dB 7 }3|3dC|%  d7 |%  dB 7 }3qt |D ]V}@t |@d D ]}A|3d*7 }3	q|@}B|3dD|(|@  dE t!|B dF t!|B|  dG 7 }3	qt jL	rt |d D ]}A|3d*7 }3	qx|3dH7 }3t |D ]&}@|3dI|(|@  dJ |(|@  d7 7 }3	q|3d:7 }3t |d D ]}A|3d*7 }3	q|3|1dK 7 }3tJ|"|D ]b\}%}$t jL
r2|3dL|$  d: 7 }3|3dM|%  d: 7 }3|3d*|%  d> |? dN |$  dO 7 }3	q|3dP7 }3t j
rtdQt|3dO|3 tdR|4t|4 i }CtM|3|4|C |C|2 }Dt j
rtdSt|DdO|D tNO|D}Et jr tdTt|E |EP  tdUt| t,| t2|EjQ}Fi }G|1gtR  |( }H|F. D ]*\}=}$|=|Hkr,|jjST|=|
j@|G|=< q,t/|EjQ|G t jr|tdV |EP  tj01|ddWg|* }It jrtdXt|IdO|I tU|EjQd }JtV||J}tU|d }Kt jLr|. D ]\}L}M|M }N|NW  |Mj}
|MjS}O|MjXD ]}P|N"|P t|Pt;jYr|PjZj@ tj[kr@qdY\|PjZj@}Qt]|Q}R|OTdZ|
}St;jYt;j^|Q|
d[|S|
d\}T|R|Sj@< |N"|T t;j_|S|PjZgd,|
d]}U|N"|U tj`jabtjc|Sj@ |PjZj@ }V|V| jj|U< q|N||L< qt jrtd^ t,| td|}Wte|||W\}X}Y|EjQtf|EjQg  }Z|ZjXd,d_ |X |ZjXd_ g |Z_Xth| | jid` }[|X|Yda|[jj|jk< t jrtdb t,| |EjQ. D ]\}L}Mtl|MjXD ]\}}Pt|Pt;jYr|PjZj@|1kr|Pj}
|MjS}Ot;m|O|
}\|MjXd,| |\_X|MjX|d d, |M_Xtf|g }]|\"t;n|]|
 |. D ]\}^}_to|_|O|EjQ|^< q6tp|g }`|M|EjQ|K< |\|EjQ|L< |EjQ|` "t;n|K|
  qqq qqt jrtdc |EP  tq|EjQ|E_Qt|EjQ t jrtdd |EP  tde| tdf |jr}a|st jrtdg d+|_rts|EjQ G dhdi ditNjt}btNju|||E|Itjc|||bdj}c|a|_rtbtjcf|I }dt jr~tdk|d |c|,|d|+|fS )la~  
    Takes a parfor and creates a gufunc function for its body.
    There are two parts to this function.
    1) Code to iterate across the iteration space as defined by the schedule.
    2) The parfor body that does the work for a single point in the iteration space.
    Part 1 is created as Python text for simplicity with a sentinel assignment to mark the point
    in the IR where the parfor body should be added.
    This Python text is 'exec'ed into existence and its IR retrieved with run_frontend.
    The IR is scanned for the sentinel assignment where that basic block is split and the IR
    for the parfor body inserted.
    rF   z'starting _create_gufunc_for_parfor_bodyc                 S   s   g | ]}|j jqS r0   )r   rE   r^   r0   r0   r1   ra      s     z2_create_gufunc_for_parfor_body.<locals>.<listcomp>zparfor_params = r:   rY   zparfor_inputs = rZ   r   Zexpanded_tuple_var_z$parfor_inputs post tuple handling = zVariable %s used in parallel loop may be written to simultaneously by multiple workers and may result in non-deterministic or unintended results.Z_arrzloop_indices = zloop_body = zparam_dict = c                    s   g | ]} | qS r0   r0   r_   r   )ind_dictr0   r1   ra     s     zind_dict = zlegal_loop_indices = zpd = z
pd type = c                    s   g | ]}t  | qS r0   )rL  rM  r   r0   r1   ra     s     c                    s   g | ]} | qS r0   r0   rM  r   r0   r1   ra     s     znew param_types:znew func_arg_types:c                    s   g | ]} | qS r0   r0   rM  
param_dictr0   r1   ra     s     FparamZ__sentinel__zlegal parfor_params = z__numba_parfor_gufunc_%s-_zgufunc_name  zdef z(sched, z, z):
)r{   rr   r  TNz	func_def:r}   znamed_tuple_def:zgval:(zname:z0Didn't find definition of namedtuple for globls.zCould not find definition of z = =,z = (c                    s   g | ]} | qS r0   r0   r_   rH  rO  r0   r1   ra     s     z)
z = np.ascontiguousarray(Z!ParallelAcceleratorGufuncThreadIdz*numba.np.ufunc.parallel._iget_thread_id()
[z]
z<    print("thread id =", ParallelAcceleratorGufuncThreadId)
zF    print("initial reduction value",ParallelAcceleratorGufuncThreadId,z.shape)
z>    print("reduction array",ParallelAcceleratorGufuncThreadId,zfor z in range(sched[z	], sched[z] + np.uint8(1)):
zprint("z",z = 0
zD    print("final reduction value",ParallelAcceleratorGufuncThreadId,zD    print("final reduction array",ParallelAcceleratorGufuncThreadId,z] = 
z    return None
zgufunc_txt = zglobls:zgufunc_func = zgufunc_ir dump zloop_body dump zgufunc_ir dump after renaming rE  zgufunc_param_types = z{} =rP   )r   r>   )r   r   r>   rQ   zparfor loop bodyr   Zparfor_diagnostics)r3  r4  zAfter hoistingz#gufunc_ir last dump before renamingzgufunc_ir last dumpr   rg   z(No aliases found so adding noalias flag.c                   @   s   e Zd Zdd ZdS )z<_create_gufunc_for_parfor_body.<locals>.ParforGufuncCompilerc                 S   s\   ddl m} tj}|d}|| j}|j|j || j}|j|j |	  |gS )Nr   )PassManagerZfull_parfor_gufunc)
Znumba.core.compiler_machineryr\  r   ZDefaultPassBuilderZdefine_parfor_gufunc_pipelinestateZpassesextendZ/define_parfor_gufunc_nopython_lowering_pipelinefinalize)r,   r\  ZdpbpmZparfor_gufunc_passesZlowering_passesr0   r0   r1   define_pipelines   s    zM_create_gufunc_for_parfor_body.<locals>.ParforGufuncCompiler.define_pipelinesN)r2   r3   r4   ra  r0   r0   r0   r1   ParforGufuncCompiler  s   rb  )Zpipeline_classz5finished create_gufunc_for_parfor_body. kernel_sig = )vr   ri   rj   rn   r>   rh   r  r   rz   r   rt   rr   rs   r   rw   rf   rg   Zget_parfor_reductionsru   r   sortedr	  r  rk   r&   r   r   ZNamedUniTupler  rG   ZPARFOR_MAX_TUPLE_SIZErv   r~   r   r   Tuple
NamedTupler0  warningswarnr   replace_var_with_arrayr   rF  r  rJ  r   r   r   r   r   r   hexhashreplacejoinr{   r   r   r   r   r   r   ZArgrE   r$  ZFreeVarr   
containersZBaseNamedTuplesplitZinstance_classr!   r2   r  fieldsr   execr   Zrun_frontendrm   r  valuesr=   r   r   r
   clearro   r   r   Znumber_domainformatr   Constr   coretypingr   r   r  rC  r  r  r  metadataZ
hoist_infoidr  ZBlockr  r   r  r   Znoaliasr   ZCompilerBaseZ
compile_ir)er7   r   rg   r   r   r   localsZhas_aliasesr   rp   r>   r  Z
parfor_dimZloop_indicesr?  Zparfor_outputsr   r   Zparfor_inputsZtuple_expanded_parfor_inputsZtuple_var_to_expanded_namesZexpanded_name_to_tuple_varZnext_expanded_tuple_varZparfor_tuple_paramspiZpi_typeZtuple_countZtuple_dtypeZthis_var_expansionr   Zexpanded_nameZtuple_typesZracemsgZparfor_redarrsZparfor_red_arg_typesr   ZarrZredarraytypeZ	redarrsigZlegal_loop_indicespdZparam_typesr   Zparfor_argsZparfor_params_origZascontigZpindexZloop_body_var_tableZsentinel_nameZgufunc_nameZ
gufunc_txtZgloblstup_varZ	exp_namesZtup_typeZ	named_tupZfunc_defZnamed_tuple_defZgvalZnamed_tuple_namerE   
field_nameZgufunc_thread_id_varZeachdimindentZ	sched_dimZloclsZgufunc_funcZ	gufunc_irZ	var_tableZnew_var_dictreserved_namesZgufunc_param_typesZgufunc_stub_last_labelZ	new_labelr  r  rB  r=   r-   strvalr   r   Z
assign_lhsZ
print_noder   r@  r3  r4  Zstart_blockZdiagnosticsZ
prev_blockZbody_first_labelr`   bZbody_last_labelZ	old_aliasrb  Zkernel_funcZ
kernel_sigr0   )rN  rP  rg   r1   r     sd   

   








	











 

 
 $
	$




  



 



 













r   c                 C   s:  g }|j D ](}t|tjr|jj| kr|j}|jj}td|}|	d|}	t
j||	j< t||	|}
||
 |	d|}||jj ||j< |t|j|| t|j|	||}tt
jt
j||jj ddt
j||jj ||< || q
n2t|tjr*t| d|ji|| t| |j|| || q
|S )Nr   z$const_ind_0z$valrF   rE  )ro   r&   r   r   r   rE   r>   r=   rt  r   r   r   r   r   r8  r   r   r   r   rS   r   r'   replace_var_with_array_internalrn   r  )varsr  rg   r   rB  r-   r>   r=   Z
const_nodeZ	const_varZconst_assignZval_varZsetitem_noder0   r0   r1   replace_var_with_array_in_block  s6    
   

r  c                 C   s&   |  D ]\}}t| ||||_qd S r%   )r   r  ro   )r  r  rg   r   r  r  r0   r0   r1   r  :  s    r  c                 C   sD   t | ||| | D ],}|| }||d  tj|dd||< qd S )NrF   rE  )r  popr   r   r   )r  r  rg   r   r   Zel_typr0   r0   r1   rh  >  s
    rh  c           ]         s  j j ddlm}m} tjrjtd td|j|j	|j
|j td| td| td| td| t|\}}|j|jj}|\}}|  |||||d	d
d}|j}|j  tjrtd|| fdd}t|}t|D ]x}|| \}}}||}||}|dkst||}|||f||< tjrtd|||| t d|||| qtjd}tj|}tj|}tj } tj!}!tj| }"tj|!}#"tj!d}$"tj!d}%|%j#}&$| }'|%d |%d}(tjrtd|j& |j&r| })|"}*n|!})|#}*tj' |)"tj!|dd}+tj' |)"tj!|dd},t|D ]}|| \}}}|j#|&kr (||&}|j#|&kr (||&}|j#|&kr (||&} )||%} *| +|+"tj!|g  *| +|,"tj!|g qftj, j-tj.|!g dd}-tj, j-tj.tj/ |!gdd}.t, j-tj.tjtj j0g d}/ 1|/g }0 1|-g }1t2  3d|0|0#d$ t d|0 j45 t6d W 5 Q R X tj.|!|!|!|"|"g}2tj, j-|2dd}3 1|3|0"tj!||+|,g}4 1|.|$g "tj!|d }5 7|4|5}6 j8|)|6d d}7tjrbdnd}8tj.|"|!|"|"|!|*| g}9|j&rtj, j-|9d!d}:ntj, j-|9d"d}: 1|:"tj!||+|,|4|7"tj |8g fd#d$|D };t|}<t||< }= fd%d&fd'd$|d(|= D |; }>t|>}?t|d }@tj' |"tj d|? d)d}g }A * 9|7|| |A:"tj |' i }Bt|?D ]J}|>| }C|| }D|| }E +|"tj |d g}F||=kr@;|E |C}Gt< |Gj=|Ej>}Htt|HD ]}I|A:|H|I  q * 9|Gj?||F qt@|EtjAr0|D|kr|EjBtjCkrrD|EjBn
tjd}Jt' |J}K *|C|K  * 9|K||F |C|Kf|B|D< |A:"tj $|J n\;|E |C}Gt< |Gj=|Ej>}Htt|HD ]}I|A:|H|I  q * 9|Gj?||F n||@k rt@|EtjEr`|Ej#}LF |C|E|L}Cn|E}Lt@|LtjGs|D|Ln
tjd}Jt' |J}M *|C|M n0t@|EtjGsD|En
tjd}Jt' |J}M * 9|M||F qi }Ng }O|(d g}O"tj d| |N|(d < t|t|>ks,tt|t|ksBtt|t|| ks\tt|t|jdd( ks|ttH||>||| D ]\}D}C}E}Pt@|EtjIjJr|Ej>t|P }nd}tjrtd*|Dd+|Pd,|Ed-| |PD ]}Qtjrtd.|Dd/|E |D|k	r"tj d|N|Q< n0;|E |C}Gt< |GjK|Ej>}R|R| |N|Q< |Q|Ok	rtj	rtd0|Qd1| t |Qd2 |N|Q  |O:|Q |d }qqt|Nd }Stj' | |Sd3d}R *|4|R d}|OD ]P}Qtj	rt |Qd2 |N|Q   *|N|Q  +|R"tj |g |d }	q|?d t|A }Ttj' | "tj |Td4d}U *"tj d| |' |U t|?D ]2}|$}V +|U"tj d| g}F *|V|F 
qptt|AD ]6}I +|U"tj d|? |I g}F *|A|I |F 
qtL|}Wtj.tj/ ||"|"|g}Xt, j-|X|}YjMN|j tjrBt d5|Y  1|Y||R|U|Wg tjrlt d6|Y  1|.|1g |BO D ]B\}Z}[|[\}C}K +|K"tj dg}\ * P|\Q|Z qjMN|j d(S )7zF
    Adds the call to the gufunc function from the main function.
    r   )build_gufunc_wrapper_launch_threadsZmake_parallel_loopzouter_sig = rb   	expr_argsexpr_arg_typesr   FT)cacheZ
is_parforszparallel function = c                    s*   t | tjr| jS  tj| S d S r%   )r&   r   rq   r   rE   get_constantr   r   )r   )rd   r7   r0   r1   
load_rangek  s    z(call_parallel_gufunc.<locals>.load_rangerF   z'call_parallel_gufunc loop_ranges[{}] = zloop range[{}]: %d %d (%d)
   z%Parfor has potentially negative start
dim_starts)sizerE   	dim_stopsZget_parallel_chunksizerJ   Zset_parallel_chunksizer   z<=znum_threads: %d
)z@Invalid number of threads. This likely indicates a bug in Numba.get_sched_size   rX   Zdo_scheduling_signedZdo_scheduling_unsignedc                    s   g | ]}  | jqS r0   )r   rE   rX  )r7   
redarrdictr0   r1   ra     s     z(call_parallel_gufunc.<locals>.<listcomp>c                    s<   | kr.|  \}} |} ||}|S  | S dS )a?  Given a variable name, if that variable is not a new name
           introduced as the extracted part of a tuple then just return
           the variable loaded from its name.  However, if the variable
           does represent part of a tuple, as recognized by the name of
           the variable being present in the exp_name_to_tuple_var dict,
           then we load the original tuple var instead that we get from
           the dict and then extract the corresponding element of the
           tuple, also stored and returned to use in the dict (i.e., offset).
        N)r   Zextract_value)rH  Zorig_tupoffsetr}  res)re   r   r7   r0   r1   load_potential_tuple_var  s    

z6call_parallel_gufunc.<locals>.load_potential_tuple_varc                    s   g | ]} |qS r0   r0   rX  )r  r0   r1   ra   	  s     NZpargszvar =zgu_sig =ztype =zi =zvar = z type = z
dim_sym = z, i = z = %d
ZpshapeZpstepszbefore calling kernel %p
zafter calling kernel %p
)Rrd   re   rc   r  r  r   ri   rj   rA   return_typeZrecvrZpysigr   Znormalize_signatureZlibraryZget_functionrf   Zllvm_func_namerE   Z_ensure_finalizedrz   r~   rv   rs  r	   Zprintfllvmliter   ZIntTypeZPointerTyper   r   rS   r   r  rk   Zget_abi_sizeofr  signedr   Zsextsubr   ZgepZget_or_insert_functionmoduleFunctionTypeZVoidTypeZbitwidthr}   Zif_unlikelyZicmp_signedZ	call_convZreturn_user_excRuntimeErrormulZallocaZbitcastr   Z
make_arrayZunpack_tuplestridesr   datar&   rK  rG   booleanZget_data_typeOptionalcastBooleanr  r   r   rI   Zget_null_valueZactive_code_libraryZadd_linking_libraryr   loadZgetvar)]r7   Zcresr   Z	outer_sigr  r  r   rx   ry   r  rn   r   rp   r   r  r  rA   r  Z	llvm_funcsinZsoutinfoZwrapper_namer  Znum_dimr   r[   r\   r]   Zbyte_tZ
byte_ptr_tZbyte_ptr_ptr_tZintp_tZuintp_tZ
intp_ptr_tZuintp_ptr_tzerooneZone_typeZsizeof_intpZ	sched_sigZ
sched_typeZsched_ptr_typer  r  Zget_chunksizeZset_chunksizer   Znum_threadsZcurrent_chunksizeZget_sched_size_fntyr  Znum_divisions
multiplierZ
sched_sizerX   Z
debug_flagZscheduling_fntyZdo_schedulingr   r   ZninoutsZall_argsnum_argsZnum_inpsZarray_stridesZrv_to_arg_dictr  r   ZatydstZaryr  r   rD   Zrv_argZunpacked_atyZptrZsig_dim_dictoccurrencesZgu_sigZdim_symZshapesZnshapesZ	num_stepsZstepsZstepsizer  Zfntyr   kr   Zonly_elem_ptrr0   )re   rd   r   r  r7   r  r1   r   E  s    




 
   


        

      









  


      

 r   )Zrh   r   r   r%  rf  dataclassesr   Zllvmlite.irr  rW   r{   rr   Znumba.parforsr   Z
numba.corer   r   r   r   r	   Znumba.core.ir_utilsr
   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   Znumba.core.typingr   r   Znumba.parfors.parforr   Znumba.core.errorsr   r    r!   r"   Z#numba.parfors.parfor_lowering_utilsr#   ZLowerr$   r(   r8   r   r   r   r   r   r   r   r   r   r   r   r  r  r  r  r"  r*  r+  r,  r-  r7  r9  r:  r>  rC  rD  r   rF  rJ  rL  r   r  r  rh  r   r0   r0   r0   r1   <module>   s    P  W$&4#E>
	4    %