o
    I&ic                     @   s   d dl Z d dlZd dlZd dl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 ddlmZ dZdZdZdZd	Zd
ZdZdZdZdZ ej!ddG dd dZ"ej!G dd dZ#dd Z$G dd dZ%dS )    N)AnycastDictListOptionalTuple   )	create_call_functioncreate_call_methodcreate_dup_topcreate_instructioncreate_jump_absoluteInstructionInstructionExnTabEntrytransform_code_object	unique_id)ExactWeakKeyDictionary                @         i   T)frozenc                   @   sH   e Zd ZU eed< dZeeedf  ed< de	e
 fddZdd	 ZdS )
ReenterWithstack_indexN.target_valuescleanupc                    s$  g }| j rdd | j D }td| j   |d vr$|d   f7  < dD ]}||d vr7|d  |f7  < q&ttjdk r@dnd	}td}g |tt|d
td dtd dtdddtdtd}tjdk r{|	td|d ntd}td}	t
||	|| jd d|_|	|  fdd}
tjdk rtdtd|g|
 td}nXtjdk rtdg|
 td|d||
 td|}n9tddd}tdd d}t
|||| jd! d
|_|	g|
 td|d||
 ||td"tddd|}|| |d#d#< |S )$z
        Codegen based off of:
        load args
        enter context
        try:
            (rest)
        finally:
            exit context
        c                 S      g | ]}t d |dqS 
LOAD_CONSTargvalr   .0val r)   IC:\wamp64\www\opt\env\Lib\site-packages\torch/_dynamo/resume_execution.py
<listcomp>4       
z*ReenterWith.try_except.<locals>.<listcomp>Z___context_manager_co_varnames)	__enter____exit__co_names      NOPPUSH_EXC_INFOT
STORE_FASTr#   	LOAD_FASTLOAD_METHODr.   r   POP_TOPSETUP_FINALLYtargetr   Fc                      s:   t d dt dddt dd dt t gtdt dS )Nr7   r#   r8   r/   r"   r2   r9   )r   r   r
   r)   Zctx_namer)   r*   create_reset^   s   


z,ReenterWith.try_except.<locals>.create_resetr2   	   	POP_BLOCKBEGIN_FINALLYEND_FINALLYJUMP_FORWARDRERAISEargCOPYr2   r   
POP_EXCEPTN)r   r   r   r   sysversion_infor	   lenr
   appendr   exn_tab_entry)selfcode_optionsr   	load_argsnameZexcept_jump_targetcleanup_complete_jump_targetZsetup_finallyZexn_tab_beginZexn_tab_endr>   epilogueZfinally_exn_tab_endZfinally_exn_tab_targetr)   r=   r*   
try_except(   s   













	
zReenterWith.try_exceptc                 C   s  g }| j rdd | j D }tjdk rEtd}td}td||tdtdg| |d	d	< g |td
t|dtd|dtdd	fS tjdk rtd}td}td}tdtdd	dtdtdtd
ddtdtd|d|td|dtd|tdtdtdtd|g| |d	d	< g |td
t|dtd|dtdd	fS td}td}dd }	td}
td}td}tddd}tddd}t|
||| jd d |
_t|||| jd d |_t|||| jd d |_||	 |	 |	 gtdd!tdtd|d|tdtd"|d||tdtddd|tdtdtd|| |d	d	< g |tt|d td#|
|fS )$zR
        Codegen based off of:
        with ctx(args):
            (rest)
        c                 S   r    r!   r%   r&   r)   r)   r*   r+      r,   z(ReenterWith.__call__.<locals>.<listcomp>r?   ZWITH_CLEANUP_STARTrB   rA   ZWITH_CLEANUP_FINISHrC   NCALL_FUNCTIONrF   
SETUP_WITHr;   r9   r1   WITH_EXCEPT_STARTr4   r"   r#   DUP_TOPr2   rD   POP_JUMP_IF_TRUErE   rI   c                   S   s   t dd dS )Nr"   r#   r%   r)   r)   r)   r*   create_load_none   s   z.ReenterWith.__call__.<locals>.create_load_noner5   r   rH   r   TFZPOP_JUMP_FORWARD_IF_TRUEZBEFORE_WITH)	r   rJ   rK   r   rL   r   r   rN   r	   )rO   rP   r   rQ   Zwith_cleanup_startZbegin_finallyZwith_except_startZpop_top_after_with_except_startrS   r[   Zexn_tab_1_beginZexn_tab_1_endZexn_tab_1_targetZexn_tab_2_endZexn_tab_2_targetr)   r)   r*   __call__   s  






	
	

zReenterWith.__call__)__name__
__module____qualname__int__annotations__r   r   r   r   r   r   rU   r\   r)   r)   r)   r*   r   !   s
   
 mr   c                   @   s`   e Zd ZU ejed< ejedZ	e
e ed< ejedZe
e ed< dZeeeef  ed< dS )ResumeFunctionMetadatacode)default_factoryinstructions prefix_block_target_offset_remapNblock_target_offset_remap)r]   r^   r_   typesCodeTypera   dataclassesfieldlistre   r   r   rf   r`   rg   r   r   r)   r)   r)   r*   rb     s   
 
rb   c                 C   sV   t |}g }zt|}| D ]}|||r|| t|}qW |S  ty*   Y |S w )z
    Two-pointer conditional filter.
    e.g. _filter_iter(insts, sorted_offsets, lambda i, o: i.offset == o)
    returns the instructions with offsets in sorted_offsets
    )iternextrM   StopIteration)l1l2Zconditrescurr(   r)   r)   r*   _filter_iter'  s   

ru   c                   @   s   e Zd Ze Ze Zedd Zedede	e dede	e
 de	e de	e d	ejfd
dZed	ee fddZedede	edf fddZdS )ContinueExecutionCachec                 G   sX   || j vrt | j |< t|}|| j | vr%| j||g|R  | j | |< | j | | S N)cachedicttuplegenerate)clsrc   linenokeyr)   r)   r*   lookup>  s   
zContinueExecutionCache.lookupoffsetsetup_fn_target_offsetsnstackargnames	setup_fns
null_idxesreturnc	                    s   d usJ |j ttB tB tB @ rJ |j t@ sJ |tjv r+| 	S t	j
dkt|dtt dtttf f 	f
dd}	t||	}
tj|
< |
S )Nr1   re   rP   c                    s  t | _dd tD    fddD  t|d p!g t|d p(g  }d|d  |d< r?d|d	  |d	< |d
< t |d< ||d< t |d< d|d< d|d< t  fdd|d D  |d< |d ttB  @ |d< t	fdd| D }g }r|r|
tdt|d |
tddd g }dd 
D }	fddt
D }dd | D }i }	d}
tD ]a}|
tk r|
 ||
 kr|
td |
d7 }
|
tk r|
 ||
 ks|
tdd| d ||v r||}|||\}}|| r||}|| }j
| ||	|< qr+ttj_|r0J |
t| | D ]}|j|jkrD nd |_tjdkrPd |_q9|rb|| || |	rsjJ | D ]}|jr|jj|	v r|	|jj |j_ql||  | d d < d S ) Nc                 S   s   g | ]}d | qS )___stackr)   r'   ir)   r)   r*   r+   k  s    zCContinueExecutionCache.generate.<locals>.update.<locals>.<listcomp>c                 3   s    | ]	}| vr|V  qd S rw   r)   r'   vargsr)   r*   	<genexpr>l  s    zBContinueExecutionCache.generate.<locals>.update.<locals>.<genexpr>co_cellvarsco_freevarsZ
resume_in_co_nameZco_qualnameco_firstlinenoco_argcountr   co_posonlyargcountco_kwonlyargcountc                    s   g | ]}| vr|qS r)   r)   r   r   r)   r*   r+   z  s    r-   co_flagsc                 3       | ]
}|j  kr|V  qd S rw   r   r   r   r)   r*   r         ZCOPY_FREE_VARSrF   RESUMEc                 S      i | ]}|j |qS r)   r   )r'   fnr)   r)   r*   
<dictcomp>      zCContinueExecutionCache.generate.<locals>.update.<locals>.<dictcomp>c                    s   i | ]
\}}|j  | qS r)   r   )r'   r   r   )r   r)   r*   r     s    
c                 S   r   r)   r   )r'   instr)   r)   r*   r     r   Z	PUSH_NULLr   r7   r   r#   r1   )copydeepcopyre   rangeextendrz   rL   
CO_VARARGSCO_VARKEYWORDSrn   rM   r   	enumeratepoprf   rl   reversedr   r   starts_linerJ   rK   Z	positionsunreachable_codesrN   r<   )re   rP   Zfreevarsr<   prefixr   hooksZhook_target_offsetsZoffset_to_instZold_hook_target_remapZnull_idxes_ir   hookZ
hook_instsZ
exn_targetZhook_target_offsetZold_hook_targetr   
r   r|   Zis_py311_plusr}   metar   r   r   r   r   r   r*   updateh  s   










z/ContinueExecutionCache.generate.<locals>.update)r   CO_GENERATORCO_COROUTINECO_ITERABLE_COROUTINECO_ASYNC_GENERATORCO_OPTIMIZEDrv   generated_code_metadata&generate_based_on_original_code_objectrJ   rK   rb   r   r   r   strr   r   )r|   rc   r}   r   r   r   r   r   r   r   Znew_coder)   r   r*   r{   G  s.   

4
d
zContinueExecutionCache.generatec                 C   s   t dddt dddgS )zACodegen a `raise None` to make analysis work for unreachable coder"   Nr#   RAISE_VARARGSr   rF   r%   )rP   r)   r)   r*   r     s   

z(ContinueExecutionCache.unreachable_codes.c                    s   t j| ddtt dtttf ffdd}t|| tj	dkrOj
sDi   _
dtt dtttf f fdd}t|| t fd	d
D t jj|g|R  S )a>  
        This handles the case of generating a resume into code generated
        to resume something else.  We want to always generate starting
        from the original code object so that if control flow paths
        converge we only generated 1 resume function (rather than 2^n
        resume functions).
        Nre   rP   c                    sR   fdd| D \  fddt t| tjD \} j|jks$J |jd S )Nc                 3   r   rw   r   r   r   r)   r*   r     r   ziContinueExecutionCache.generate_based_on_original_code_object.<locals>.find_new_offset.<locals>.<genexpr>c                 3   s     | ]\}}| u r|V  qd S rw   r)   )r'   i1i2r;   r)   r*   r     s    )zipr   re   opcoder   )re   rP   
new_target)r   
new_offsetr   r;   r*   find_new_offset  s   

zVContinueExecutionCache.generate_based_on_original_code_object.<locals>.find_new_offsetr1   c           
         s   g }| D ]}t |t jkr n|jdkr|| qt|jD ]\}}|tt|j< q"|r9tt|d jnd t fddD }t	| |dd }t	tt
| t
j|dd }t||D ]\}}	|d j|	j< qcd S )	Nr5   c                 3   s    | ]	}| kr|V  qd S rw   r)   r'   nZold_start_offsetr)   r*   r     s    zmContinueExecutionCache.generate_based_on_original_code_object.<locals>.remap_block_offsets.<locals>.<genexpr>c                 S   s
   | j |kS rw   r   )r   or)   r)   r*   <lambda>!  s   
 zlContinueExecutionCache.generate_based_on_original_code_object.<locals>.remap_block_offsets.<locals>.<lambda>c                 S   s   | d |u S )Nr   r)   )v1v2r)   r)   r*   r   &  s    r   )rL   rf   opnamerM   r   r   r`   r   sortedru   r   re   )
re   rP   Zprefix_blocksr   r   Zold_inst_offsetstargetsZnew_targetsnewold)rg   r   r   r   r*   remap_block_offsets  s:   


zZContinueExecutionCache.generate_based_on_original_code_object.<locals>.remap_block_offsetsc                 3   s    | ]} | V  qd S rw   r)   r   )rg   r)   r*   r   .  s    
zPContinueExecutionCache.generate_based_on_original_code_object.<locals>.<genexpr>)rv   r   r   r   r   r   r   r   rJ   rK   rg   rz   r   rc   )r|   rc   r}   r   r   r   r   r   r)   )rg   r   r   r   r   r*   r     s6   





*
z=ContinueExecutionCache.generate_based_on_original_code_objectN)r]   r^   r_   r   rx   r   classmethodr   r`   r   r   r   rh   ri   r{   staticmethodr   r   r   r   r)   r)   r)   r*   rv   :  s<    
	
 	
rv   )&r   rj   rJ   rh   typingr   r   r   r   r   r   Zbytecode_transformationr	   r
   r   r   r   r   r   r   r   utilsr   r   ZCO_NEWLOCALSr   r   	CO_NESTEDr   Z	CO_NOFREEr   r   r   	dataclassr   rb   ru   rv   r)   r)   r)   r*   <module>   s4     ,
 v }