U
    9%e%3                     @   s   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	m
Z
 ddlmZmZmZmZmZmZ ddlmZ ddlmZmZmZ ddl
mZmZ dd	lmZ dd
lmZ ddlmZm Z m!Z!m"Z"m#Z# ej$G dd dZ%G dd dZ&dS )    N)List   )utils)create_call_functioncreate_dup_topcreate_instructioncreate_load_globalcreate_rot_nInstruction)unimplemented)
AttrSourceGeneratorStateSourceSource)is_safe_constantrot_n_helper)VariableTracker)NNModuleVariable)NumpyNdarrayVariableSymNodeVariableTensorVariableTensorWithTFOverrideVariableUnspecializedPythonVariablec                   @   s,   e Zd ZU eed< eed< edddZdS )GraphOutputEntryindexvariable)otherc                 C   s   | j || _ d S N)r   add_options)selfr    r   T/var/www/html/Darija-Ai-API/env/lib/python3.8/site-packages/torch/_dynamo/codegen.pymerge&   s    zGraphOutputEntry.mergeN)__name__
__module____qualname__int__annotations__r   r!   r   r   r   r    r   !   s   
r   c                   @   s"  e Zd ZdZdAejjedddZdd Z	dBd	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d Zdd  Zd!d" ZdCd$d%Zd&d' Zd(d) ZeZd*d+ Zd,d- ZdDd/d0Zd1d2 Zd3d4 ZdEee j!e"d5d6d7Z#d8d9 Z$ee%e& d:d;d<Z'd=d> Z(d?d@ Z)dS )F	PyCodegenz<
    Helper class uses for constructing Python bytecode
    N)rootgraph_output_varc                 C   sb   || _ d | _t | _t | _g | _|p,i | _|| _	|| _
| j	jj| _| j	j| _| j	jj| _d S r   )r(   top_of_stackcollectionsCounterusesOrderedDictgraph_outputs_outputtempvarstxr)   outputcode_optionscell_and_freevarsnew_var)r   r2   r(   r)   r1   r   r   r    __init__0   s    



zPyCodegen.__init__c                 C   s   dd | j  D S )Nc                 S   s   g | ]
}|j qS r   )r   .0xr   r   r    
<listcomp>D   s     z/PyCodegen.graph_output_vars.<locals>.<listcomp>)r/   valuesr   r   r   r    graph_output_varsC   s    zPyCodegen.graph_output_varsTc           	      C   s>  t |tr(| j||  |   dS | jjj	|j t |t
sHt| j}| j}| j|krn|t  dS |r|jr|j| jkr|| | j|j  || _dS | j|dk	r|| | j|  || _dS |jdk	r|rt |jts||j|  n(| r<t| r<|| |  nt |tr|j}| |}|| j| ddd | || j  |t!dd nt |t"t#t$t%fr0| |}t |t%r| &t'j(d | || j  t |t%r|t!dd n0t |t$r4|j)r4|| *dgt!dd  nt |t+r|j,-d}|d | j.d	 kr~|| |d  |dd }n"| j/dk	st|| 0| j/ |D ]}|| *| qnv| j1|  d7  < z|||  W n$ t2k
r   t3d
|  Y nX |r4|| jkr4| jt  | 4| || _dS )z:Generate code such that top-of-stack (TOS) is set to valueNTaddr   Zto_numpy_helperitemr   .co_varnameszreconstruct: )5
isinstancer   r0   extendreconstruct	clear_tosr2   r3   Zguardsupdater   AssertionErrorr/   r*   appendr   mutable_localr1   create_loadgetsourcer   Zis_python_constantr   Zas_python_constantcreate_load_constr   tensor_variableadd_graph_outputr   Zglobal_class_nameload_graph_outputr   r   r   r   r   r   load_import_fromr   r"   Zneed_unwrapcreate_load_attrr   Z
module_keysplitr4   r(   create_load_outputr-   NotImplementedErrorr   	add_cache)	r   valueZallow_cacher3   r/   rP   graph_outputs_keypartspartr   r   r    __call__F   s    



	

zPyCodegen.__call__c                 C   sB   t | }|| jkr.tt| j|| j|< n| j| | |S r   )idZas_proxyr/   r   lenr!   )r   rY   rZ   r   r   r    rQ      s    
 zPyCodegen.add_graph_outputc                 C   s:   | j }|| | j || | |td d S )NBINARY_SUBSCR)r0   rJ   rL   r)   _create_load_constr   )r   r   r3   r   r   r    rR      s    zPyCodegen.load_graph_outputc                 C   s:   |   }|| j|< |jr$|| j|j< | j| | d S r   )r6   r1   rK   r0   rJ   create_store)r   rY   varr   r   r    rX      s
    
zPyCodegen.add_cachec                 C   s   |D ]}| | qd S r   r   )r   itemsir   r   r    foreach   s    zPyCodegen.foreachc                 C   sR   t dd|}| jj}||kr8t|| t|ks@tn|||< | j||ddgS )zStore value in a new globalz[^a-zA-Z0-9_]+_Tr?   )resubr2   	f_globalsr^   rI   r   )r   namerY   	push_nullrj   r   r   r    setup_globally_cached   s    zPyCodegen.setup_globally_cachedc                 C   s
   d | _ d S r   )r*   r=   r   r   r    rG      s    zPyCodegen.clear_tosc                 C   s&   t |tst| j| |   d S r   )rD   r
   rI   r0   rJ   rG   )r   instr   r   r    append_output   s    zPyCodegen.append_outputc                 C   s.   t dd |D st| j| |   d S )Nc                 s   s   | ]}t |tV  qd S r   )rD   r
   r8   r   r   r    	<genexpr>   s     z*PyCodegen.extend_output.<locals>.<genexpr>)allrI   r0   rE   rG   )r   Zinstsr   r   r    extend_output   s    zPyCodegen.extend_outputc                 C   s   | j S r   )r0   r=   r   r   r    get_instructions   s    zPyCodegen.get_instructionsc                 C   s@   ||   krtd|dS || jd ks4t| dtd|dS )N
LOAD_DEREFargvalrC   z missing	LOAD_FASTr5   r   r4   rI   r   rk   r   r   r    rL      s    zPyCodegen.create_loadc                 C   s   ||   ksttd|dS )NLOAD_CLOSUREru   )r5   rI   r   ry   r   r   r    create_load_closure   s    zPyCodegen.create_load_closurec                 C   s6   ||   krtd|dS || jd ks*ttd|dS )NSTORE_DEREFru   rC   
STORE_FASTrx   ry   r   r   r    rb      s    zPyCodegen.create_storeFc                 C   s8   |r| j j| || jd ks.t| dt||S )Nco_namesz not in co_names)r2   r3   Zupdate_co_namesr4   rI   r   )r   rk   rl   r@   r   r   r    r      s    zPyCodegen.create_load_globalc                 C   s    t |std| | |S )Nzunsafe constant )r   rI   ra   r   rY   r   r   r    rO      s    zPyCodegen.create_load_constc                 C   s   t d|dS )N
LOAD_CONSTru   )r   r   r   r   r    ra      s    zPyCodegen._create_load_constc                 C   s.   || j d kr"| j d  |f7  < td|dS )Nr~   	LOAD_ATTRru   )r4   r   ry   r   r   r    rT      s    zPyCodegen.create_load_attrc                    s    fdd| dD S )Nc                    s   g | ]}  |qS r   )rT   )r9   rk   r=   r   r    r;      s     z/PyCodegen.create_load_attrs.<locals>.<listcomp>rB   )rU   )r   namesr   r=   r    create_load_attrs   s    zPyCodegen.create_load_attrsr   c                 C   sZ   g }|r0t jdkr0|tdf| |d  || j|dddf| |d  |S )z6Load the global fn_name on the stack num_on_stack down      	PUSH_NULLr   FTr?   )sysversion_inforE   r   rot_nr   )r   fn_namerl   num_on_stackr3   r   r   r    load_function_name   s    zPyCodegen.load_function_namec              
   C   s\   z
t |W S  tk
rV   td|d| t|ft dtdddtd|df Y S X d S )NBUILD_TUPLEarg   CALL_FUNCTION_EXr   UNPACK_SEQUENCE)r	   AttributeErrorr   ra   r   )r   nr   r   r    r     s    



zPyCodegen.rot_nc                 C   s0   t jdkst| dd ftddtdfS )Nr   c                   S   s   d S r   r   r   r   r   r    <lambda>      z$PyCodegen.pop_null.<locals>.<lambda>r   FPOP_TOP)r   r   rI   ra   r   r   r=   r   r   r    pop_null  s    zPyCodegen.pop_null)r   coderl   c                 C   s   |j }|st| j}tjdkrD|rD|td || |d  |D ]&}|| 	 ks\t|td|d qH|tdt
|d || | tjdk r|| | |tdd	d || |d  |   d S )
Nr   r   r   rz   ru   r   r   MAKE_FUNCTION   )co_freevarsrI   r0   r   r   rJ   r   rE   r   r5   r_   rO   rG   )r   r   r   rl   r   Zfreevarsr3   rc   r   r   r    make_function_with_closure"  s     
z$PyCodegen.make_function_with_closurec                 C   sv   | j jj}tdd|j}||d|kr:| j||ddS d| dt| }||krf| j j	|| | j||ddS )zT
        Generate a LOAD_GLOBAL instruction to fetch a given python module.
        z^.*[.] NTr?   Z
___module_rg   )
r2   r3   global_scoperh   ri   r"   rM   r   r^   Zinstall_global)r   modrl   r   rk   Zmangled_namer   r   r    create_load_python_module6  s    
z#PyCodegen.create_load_python_module)r   returnc                 C   s   |  | |d | jjj}|D ]X}|jrh|  | td| dg |  |	|  |  t
dd q |  |	|  q |  t
t|d dS )z2Call the generated code function stored in fn_nameTZ	as_tensorr   FN)rr   r   r2   r3   	graphargsZis_unspecializedr   torchrT   loadr   r_   )r   r   r   r   r   r   r    make_call_generated_codeC  s    

z"PyCodegen.make_call_generated_codec                 C   s"   |  t| j|||  d S r   )rr   r   r2   Zimport_sourcerF   )r   module_nameZobject_namer   r   r    rS   W  s
    zPyCodegen.load_import_fromc                 C   sX   t jdkrBt||}|d jdks&ttd|d}|d| |S | |td|dgS )Nr   ZPRECALLZKW_NAMESru   CALL_FUNCTION_KWr   )r   r   r   opnamerI   r   insertrO   )r   nargsZkw_namesrl   r3   Zkw_names_instr   r   r    create_call_function_kw^  s    


z!PyCodegen.create_call_function_kw)NNNN)T)F)r   )r   )*r"   r#   r$   __doc__r   nnModulestrr7   r>   r]   rQ   rR   rX   rf   rm   rG   ro   rr   rs   rL   r{   rb   r   rO   ra   rV   rT   r   r   r   r   typesCodeTypeboolr   r   r   r
   r   rS   r   r   r   r   r    r'   +   sT       
Y


   r'   )'r+   dataclassesrh   r   r   typingr   Ztorch.nnr   r   r   Zbytecode_transformationr   r   r   r   r	   r
   excr   rN   r   r   r   r   r   Zvariables.baser   Zvariables.nn_moduler   Zvariables.tensorr   r   r   r   r   	dataclassr   r'   r   r   r   r    <module>   s"    		