U
    ÷¾|e):  ã                   @   sf  d 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m	Z	m
Z
mZ ddlmZ G dd„ deƒZG dd	„ d	eƒZed
ƒZejZejZejZejZejZejZejZdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ ZG dd„ deƒZ G dd„ deƒZ!d2dd„Z"dd„ Z#dd „ Z$d!d"„ Z%e &d#d$¡Z'ej(d%d&„ ƒZ)d'd(„ Z*d)d*„ Z+d+d,„ Z,ej(d3d.d/„ƒZ-d0d1„ Z.dS )4z<
Utilities to simplify the boilerplate for native lowering.
é    N)ÚEnum)ÚtypingÚtypesÚutilsÚcgutils)ÚBaseRegistryLoaderc                   @   sb   e Zd ZdZd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dS )ÚRegistryz?
    A registry of function and attribute implementations.
    Úunspecifiedc                 C   s(   || _ g | _g | _g | _g | _g | _d S ©N)ÚnameÚ	functionsÚgetattrsÚsetattrsÚcastsÚ	constants)Úselfr   © r   úP/var/www/website-v5/atlas_env/lib/python3.8/site-packages/numba/core/imputils.pyÚ__init__   s    zRegistry.__init__c                    s   ‡ ‡‡fdd„}|S )a1  
        Decorate an implementation of *func* for the given argument types.
        *func* may be an actual global function object, or any
        pseudo-function supported by Numba, such as "getitem".

        The decorated implementation has the signature
        (context, builder, sig, args).
        c                    s   ˆj  | ˆˆ f¡ | S r
   )r   Úappend©Úimpl©ÚargtysÚfuncr   r   r   Údecorate%   s    z Registry.lower.<locals>.decorater   )r   r   r   r   r   r   r   Úlower   s    	zRegistry.lowerc                 C   s"   ||||ƒ}|  |||jf¡ |S r
   )r   Ú	signature)r   r   ÚtyÚattrZ	impl_listÚ	decoratorÚ	real_implr   r   r   Ú_decorate_attr*   s    zRegistry._decorate_attrc                    s   ‡ ‡‡fdd„}|S )zÏ
        Decorate an implementation of __getattr__ for type *ty* and
        the attribute *attr*.

        The decorated implementation will have the signature
        (context, builder, typ, val).
        c                    s   ˆ  | ˆˆ ˆjt¡S r
   )r"   r   Ú_decorate_getattrr   ©r   r   r   r   r   r   7   s    ÿz(Registry.lower_getattr.<locals>.decorater   ©r   r   r   r   r   r$   r   Úlower_getattr/   s    zRegistry.lower_getattrc                 C   s   |   |d¡S )a:  
        Decorate the fallback implementation of __getattr__ for type *ty*.

        The decorated implementation will have the signature
        (context, builder, typ, val, attr).  The implementation is
        called for attributes which haven't been explicitly registered
        with lower_getattr().
        N)r&   ©r   r   r   r   r   Úlower_getattr_generic<   s    	zRegistry.lower_getattr_genericc                    s   ‡ ‡‡fdd„}|S )zÐ
        Decorate an implementation of __setattr__ for type *ty* and
        the attribute *attr*.

        The decorated implementation will have the signature
        (context, builder, sig, args).
        c                    s   ˆ  | ˆˆ ˆjt¡S r
   )r"   r   Ú_decorate_setattrr   r$   r   r   r   O   s    ÿz(Registry.lower_setattr.<locals>.decorater   r%   r   r$   r   Úlower_setattrG   s    zRegistry.lower_setattrc                 C   s   |   |d¡S )a;  
        Decorate the fallback implementation of __setattr__ for type *ty*.

        The decorated implementation will have the signature
        (context, builder, sig, args, attr).  The implementation is
        called for attributes which haven't been explicitly registered
        with lower_setattr().
        N)r*   r'   r   r   r   Úlower_setattr_genericT   s    	zRegistry.lower_setattr_genericc                    s   ‡ ‡‡fdd„}|S )zÖ
        Decorate the implementation of implicit conversion between
        *fromty* and *toty*.

        The decorated implementation will have the signature
        (context, builder, fromty, toty, val).
        c                    s   ˆj  | ˆ ˆff¡ | S r
   )r   r   r   ©Úfromtyr   Útotyr   r   r   g   s    z%Registry.lower_cast.<locals>.decorater   )r   r-   r.   r   r   r,   r   Ú
lower_cast_   s    zRegistry.lower_castc                    s   ‡ ‡fdd„}|S )z¸
        Decorate the implementation for creating a constant of type *ty*.

        The decorated implementation will have the signature
        (context, builder, ty, pyval).
        c                    s   ˆ j  | ˆff¡ | S r
   )r   r   r   r'   r   r   r   s   s    z)Registry.lower_constant.<locals>.decorater   )r   r   r   r   r'   r   Úlower_constantl   s    zRegistry.lower_constantc                 C   s   d| j › d�S )NzLowering Registry<ú>)r   ©r   r   r   r   Ú__repr__x   s    zRegistry.__repr__N)r	   )Ú__name__Ú
__module__Ú__qualname__Ú__doc__r   r   r"   r&   r(   r*   r+   r/   r0   r3   r   r   r   r   r      s   
r   c                   @   s   e Zd ZdZdZdS )ÚRegistryLoaderz6
    An incremental loader for a target registry.
    )r   r   r   r   r   N)r4   r5   r6   r7   Úregistry_itemsr   r   r   r   r8   |   s   r8   Úbuiltin_registryc                    s8   | ‰ |d k	r‡ fdd„}n‡ fdd„}|f|_ ||_|S )Nc                    s   ˆ | |||ƒS r
   r   ©ÚcontextÚbuilderÚtypÚvaluer   ©r!   r   r   Úres”   s    z_decorate_getattr.<locals>.resc                    s   ˆ | ||||ƒS r
   r   r;   r@   r   r   rA   —   s    )r   r   ©r   r   r   rA   r   r@   r   r#   �   s    r#   c                    s<   | ‰ |d k	r‡ fdd„}n‡ fdd„}|t jf|_||_|S )Nc                    s   ˆ | |||ƒS r
   r   ©r<   r=   ÚsigÚargsr   r@   r   r   rA   ¢   s    z_decorate_setattr.<locals>.resc                    s   ˆ | ||||ƒS r
   r   rC   r@   r   r   rA   ¥   s    )r   ÚAnyr   r   rB   r   r@   r   r)   ž   s    r)   c           	   	   C   st   t |jtjƒrp|jj}|  ||¡}t ||¡}| | 	|j
¡¡�  |  |||¡}| ||¡ W 5 Q R X | |¡}|S r
   )Ú
isinstanceÚreturn_typer   ÚOptionalÚtypeZmake_optional_noner   Úalloca_once_valueÚif_thenÚnot_Zis_noneZmake_optional_valueÚstoreÚload)	r<   r=   rD   ÚstatusÚretvalÚ
value_typeZoptional_noneZ	retvalptrZoptional_valuer   r   r   Úfix_returning_optional­   s      ÿ
rS   c                    s"   ‡ fdd„}ˆ j |_t|ƒ|_|S )zC
    A wrapper inserting code calling Numba-compiled *fndesc*.
    c              	      s¬   |   |jˆ ¡}| j ||ˆ jˆ j|¡\}}t ||j¡� | j 	||¡ W 5 Q R X |j
ˆ jksbt‚t| ||||ƒ}|j|  |j
¡krœd}t| |j|j
¡ƒ‚t| |ˆ j|ƒS )Nz$function returned {0} but expect {1})Údeclare_functionÚmoduleÚ	call_convÚcall_functionÚrestypeÚargtypesr   Úif_unlikelyZis_errorZreturn_status_propagaterH   ÚAssertionErrorrS   rJ   Úget_value_typeÚ	TypeErrorÚformatÚimpl_ret_new_ref)r<   r=   rD   rE   r   rP   rQ   Úmsg©Úfndescr   r   ÚimpÀ   s         ÿzuser_function.<locals>.imp)rY   r   ÚtupleÚlibs)rb   re   rc   r   ra   r   Úuser_function»   s    
rf   c                    s   ‡ fdd„}t |ƒ|_|S )zD
    A wrapper inserting code calling Numba-compiled *gendesc*.
    c                    s2   |   |jˆ ¡}| j ||ˆ jˆ j|¡\}}||fS r
   )rT   rU   rV   rW   rX   rY   )r<   r=   rD   rE   r   rP   rQ   ©Úgendescr   r   rc   Û   s        ÿzuser_generator.<locals>.imp)rd   re   )rh   re   rc   r   rg   r   Úuser_generatorÖ   s    
ri   c                    s   ‡ fdd„}|S )zl
    Decorator a given class as implementing *iterator_type*
    (by providing an `iternext()` method).
    c                    s0   ˆ j ‰ttjƒ‡ ‡fdd„ƒ}tdˆƒ|ƒ ˆ S )Nc                    s    |\}ˆ | ||ƒ}ˆ|| ||ƒS r
   r   )r<   r=   rD   rE   Úresultr?   Ziterobj©ÚclsÚiternextr   r   Úiternext_wrapperñ   s    z8iterator_impl.<locals>.wrapper.<locals>.iternext_wrapperrm   )rm   Úiternext_implÚRefTypeÚBORROWEDÚlower_builtin)rl   rn   ©Úiterator_typerk   r   Úwrapperí   s
    ziterator_impl.<locals>.wrapperr   )Úiterable_typert   ru   r   rs   r   Úiterator_implç   s    rw   c                   @   sF   e Zd ZdZdZdd„ Zdd„ Zddd	„Zd
d„ Zdd„ Z	dd„ Z
dS )Ú_IternextResultzb
    A result wrapper for iteration, passed by iternext_impl() into the
    wrapped function.
    ©Ú_contextÚ_builderÚ_pairobjc                 C   s   || _ || _|| _d S r
   ry   )r   r<   r=   Úpairobjr   r   r   r     s    z_IternextResult.__init__c                 C   s   | j  tjd¡| j_dS )z1
        Mark the iterator as exhausted.
        FN©rz   Zget_constantr   Úbooleanr|   Úsecondr2   r   r   r   Úset_exhausted	  s    z_IternextResult.set_exhaustedTc                 C   s$   |dkr| j  tj|¡}|| j_dS )z„
        Mark the iterator as valid according to *is_valid* (which must
        be either a Python boolean or a LLVM inst).
        )FTNr~   )r   Úis_validr   r   r   Ú	set_valid  s    z_IternextResult.set_validc                 C   s   || j _dS )zP
        Mark the iterator as yielding the given *value* (a LLVM inst).
        N©r|   Úfirst)r   r?   r   r   r   Úyield_  s    z_IternextResult.yield_c                 C   s   | j  | jtj| jj¡S )z>
        Return whether the iterator is marked valid.
        )rz   Zget_argument_valuer{   r   r   r|   r€   r2   r   r   r   r‚     s    
þz_IternextResult.is_validc                 C   s   | j jS )z>
        Return the iterator's yielded value, if any.
        r„   r2   r   r   r   Úyielded_value&  s    z_IternextResult.yielded_valueN)T)r4   r5   r6   r7   Ú	__slots__r   r�   rƒ   r†   r‚   r‡   r   r   r   r   rx   ý   s   
	rx   c                   @   s   e Zd ZdZdZdZdZdS )rp   z&
    Enumerate the reference type
    é   é   é   N)r4   r5   r6   r7   ÚNEWrq   Ú	UNTRACKEDr   r   r   r   rp   ,  s   rp   c                    s*   ˆ dd„ t D ƒkrtdƒ‚‡ fdd„}|S )až  
    Wrap the given iternext() implementation so that it gets passed
    an _IternextResult() object easing the returning of the iternext()
    result pair.

    ref_type: a numba.targets.imputils.RefType value, the reference type used is
    that specified through the RefType enum.

    The wrapped function will be called with the following signature:
        (context, builder, sig, args, iternext_result)
    c                 S   s   g | ]}|‘qS r   r   )Ú.0Úxr   r   r   Ú
<listcomp>I  s     z!iternext_impl.<locals>.<listcomp>z3ref_type must be an enum member of imputils.RefTypec                    s   ‡ ‡fdd„}|S )Nc              	      st   |j }|  ||¡}ˆ | |||t| ||ƒƒ ˆtjkr:t}n(ˆtjkrJt}nˆtjkrZt	}nt
dƒ‚|| ||| ¡ ƒS )NzUnknown ref_type encountered)rH   Úmake_helperrx   rp   rŒ   r_   rq   Úimpl_ret_borrowedr�   Úimpl_ret_untrackedÚ
ValueErrorÚ	_getvalue)r<   r=   rD   rE   Ú	pair_typer}   Zimpl_ret)r   Úref_typer   r   ru   M  s     

ÿ


 ÿz-iternext_impl.<locals>.outer.<locals>.wrapperr   )r   ru   ©r—   )r   r   ÚouterL  s    ziternext_impl.<locals>.outer)rp   r”   )r—   r™   r   r˜   r   ro   =  s    ro   c                 C   s&   t  |j|¡}|  d|¡}|||fƒS )z‡
    Call the `getiter()` implementation for the given *iterable_type*
    of value *val*, and return the corresponding LLVM inst.
    Úgetiter)r   r   rt   Úget_function)r<   r=   rv   ÚvalZgetiter_sigZgetiter_implr   r   r   Úcall_getiter`  s    r�   c           	      C   sR   |j }t |tj¡}t ||¡}|  d|¡}|||fƒ}|  |||¡}t| ||ƒS )z®
    Call the `iternext()` implementation for the given *iterator_type*
    of value *val*, and return a convenience _IternextResult() object
    reflecting the results.
    rm   )	Ú
yield_typer   ÚPairr   r   r   r›   r‘   rx   )	r<   r=   rt   rœ   Úitemtyr–   Ziternext_sigro   r}   r   r   r   Úcall_iternextj  s    r¡   c                 C   sB   z|   tt tj|¡¡}W n tk
r0   Y dS X |||fƒS dS )z^
    Call len() on the given value.  Return None if len() isn't defined on
    this type.
    N)r›   Úlenr   r   r   ÚintpÚNotImplementedError)r<   r=   r   rœ   Zlen_implr   r   r   Úcall_leny  s
    r¥   Ú_ForIterLoop)r?   Údo_breakc           	   
   #   sÐ   |j }t| ˆ||ƒ}ˆ d¡}ˆ d¡‰ ‡ ‡fdd„}ˆ |¡ ˆ |¡�\ t| ˆ||ƒ}ˆjˆ | ¡ ¡dd�� ˆ ˆ ¡ W 5 Q R X t	| 
¡ |ƒV  ˆ |¡ W 5 Q R X ˆ ˆ ¡ | jrÌ| j ˆ||¡ dS )zÆ
    Simulate a for loop on the given iterable.  Yields a namedtuple with
    the given members:
    - `value` is the value being yielded
    - `do_break` is a callable to early out of the loop
    zfor_iter.bodyzfor_iter.endc                      s   ˆ  ˆ ¡ d S r
   )Úbranchr   ©Zbb_endr=   r   r   r§   ˜  s    zfor_iter.<locals>.do_breakF)ÚlikelyN)rt   r�   Úappend_basic_blockr¨   Ú
goto_blockr¡   rL   rM   r‚   r¦   r‡   Úposition_at_endÚ
enable_nrtÚnrtZdecref)	r<   r=   rv   rœ   rt   ZitervalZbb_bodyr§   rA   r   r©   r   Úfor_iterŠ  s    



r°   c                 C   s   |S )z5
    The implementation returns a new reference.
    r   ©Úctxr=   ÚrettyÚretr   r   r   r_   ©  s    r_   c                 C   s   | j r| j |||¡ |S )zž
    The implementation returns a borrowed reference.
    This function automatically incref so that the implementation is
    returning a new reference.
    )r®   r¯   Zincrefr±   r   r   r   r’   °  s    r’   c                 C   s   |S )z.
    The return type is not a NRT object.
    r   r±   r   r   r   r“   »  s    r“   Únumpyc                 c   s8   ddl m} | j}| || ¡| _z
dV  W 5 || _X dS )z7
    Temporarily change the context's error model.
    r   )ÚcallconvN)Ú
numba.corer¶   Zerror_modelZcreate_error_model)r<   Ú
model_namer¶   Zold_error_modelr   r   r   Úforce_error_modelÂ  s    
r¹   c                  O   s   t dƒ‚dS )zPA stub for use internally by Numba when a call is emitted
    on a TypeRef.
    z%This function should not be executed.N)r¤   )rE   Úkwargsr   r   r   Únumba_typeref_ctorÑ  s    r»   )N)rµ   )/r7   ÚcollectionsÚ
contextlibÚinspectÚ	functoolsÚenumr   r·   r   r   r   r   Únumba.core.typing.templatesr   Úobjectr   r8   r:   r   rr   r&   r(   r*   r+   r/   r0   r#   r)   rS   rf   ri   rw   rx   rp   ro   r�   r¡   r¥   Ú
namedtupler¦   Úcontextmanagerr°   r_   r’   r“   r¹   r»   r   r   r   r   Ú<module>   sP   l	/
#
ÿ
