U
    9%e7                     @   s  d dl Z d dlZd dlZd dlZd dlZd dlZd dlZd dlZ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mZ d dlmZ d dlmZmZmZ d dlZd dl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! d d
l"m#Z# d dl$m%Z% ddl&m'Z'm(Z( ddl)m*Z*m+Z+m,Z,m-Z-m.Z. ddl/m0Z0 e1e2Z3e4ddd Z5d$ddZ6ee* ej7dddZ8ej9dd Z:G dd dZ;ee Z<G dd dZ=ej>G dd dZ?e@ ZAd d! ZBd"d# ZCdS )%    N)AnyList)patch)
draw_graphget_aot_graph_nameget_graph_being_compiled)fx)save_graph_reprowrap_compiler_debug)get_debug_dir)GraphModule)_extract_tensor_metadataTensorMetadata)legalize_graph)tree_map   )configir)BaseSchedulerNodeFusedSchedulerNodeNopKernelSchedulerNode
OutputNodeSchedulerNode)Vc                   C   s8   zt jddgt jd W dS  t jk
r2   Y dS X d S )Nwhichdot)stderrTF)
subprocesscheck_outputPIPESubprocessError r!   r!   T/var/www/html/Darija-Ai-API/env/lib/python3.8/site-packages/torch/_inductor/debug.pyhas_dot*   s
    r#   Fc           	   	   C   s   t  std dS |dkr"t }t| }|jD ]d}d|jkr@q0|jd j}t|t	r^|d }d}t|t
jrv|jj}t||ddddd}||jd< q0|rt| ti |}t| |j  t||dd dS )zR
    Draw a graph in fname.svg.
    nodes is a list of SchedulerNode objects.
    z*draw_buffers() requires `graphviz` packageNfusion_metar   Ztensor_metaF)Z
clear_meta)r#   logwarningr   create_fx_from_snodesnodesmetagroup
isinstancetupler   ZComputedBufferdatadtyper   printr   r   graphZlintr   )	r(   Zprint_graphfnamer0   noder*   r.   metadatagmr!   r!   r"   draw_buffers3   s.    





r5   )snodesreturnc                    s  dd }t ddddg}i }tj }d}g }d}| D ]$}| rPd}	|	}nZ| rbd	}	|	}nHt|trvd
}	|	}n4t|t	rd}	|j
}nt|trd}	|j
}ntdtjj| d}
|	 d|
 }||}|j|ddd} fdd  |r|| | }||_||||	|jd< t|trJ|jD ]}||| < q6|||< |dkr8|}q8| D ]}| }|jj}|| }g }|D ]T}|j|kr||j }n,|| ||j}|||j< W 5 Q R X || qt||_qd|t|dkr|d nt| |S )zB
    Creates a FX Graph from a list of SchedulerNode objects.
    c                 S   s   dd }| |_ |S )Nc                  W   s   dS )Nr   r!   )argsr!   r!   r"   func1_   s    z;create_fx_from_snodes.<locals>.get_fake_func.<locals>.func1)__name__)namer9   r!   r!   r"   get_fake_func^   s    z,create_fx_from_snodes.<locals>.get_fake_func
FusionMetar*   snodetypeNZexterntemplateZnopZcomputeZfusedzUnknown node typeZoriginal_atenz: r!   r8   kwargsc                    s6   t | tr"t fdd| jD S tdd | jD S )Nc                 3   s   | ]} |V  qd S Nr!   ).0x	in_outputr!   r"   	<genexpr>   s     z;create_fx_from_snodes.<locals>.in_output.<locals>.<genexpr>c                 s   s   | ]}t |jtV  qd S rC   )r+   r2   r   )rD   userr!   r!   r"   rH      s     )r+   r   anyr6   Zusers)r>   rF   r!   r"   rG      s    
z(create_fx_from_snodes.<locals>.in_outputr$   r   r   )collections
namedtupletorchr   GraphZ	is_externZis_templater+   r   r   r*   r   RuntimeErrorZ	_inductorutilsZget_fused_kernel_nameZ	get_nodesZcall_functionappendget_namer;   r)   r6   Zread_writesZreadsZinserting_beforeplaceholderr,   r8   outputlen)r6   r<   r=   Zbuf_to_fx_noder0   Z
first_nodeoutputsr*   r>   Z	node_typeZ
fused_name	func_nameZ	node_funcZfx_noder;   rE   depsnew_argsdepZdep_noder!   rF   r"   r'   Y   st    




 


$r'   c               	   c   s   t jdddk} dd l}t|jjj}t	
 }| sPz
d V  W 5 |  X d S |tdd t jt d}t j|st | tt j|dt  d	}|tj |td
 || z
d V  W 5 || |  X d S )NZTORCH_COMPILE_DEBUG01r   z*functorch.compile.config.debug_partitionerTtorchinductorZaot_z
_debug.log3[%(filename)s:%(lineno)d %(levelname)s] %(message)s)osenvirongetZtorch._functorch.aot_autogradlogging	getLoggerZ
_functorchZaot_autogradr:   
contextlib	ExitStackcloseenter_contextr   pathjoinr   existsmakedirsFileHandlerr   setLevelDEBUGsetFormatter	Formatter
addHandlerremoveHandler)Zcompile_debugrM   r%   stackrh   fhr!   r!   r"   enable_aot_logging   s8    





ru   c                   @   s   e Zd Ze Zedd Zedd Zdd Z	e
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S )DebugContextc                    s"   t   fdd}t|ddS )Nc               
      s(   t    | |W  5 Q R  S Q R X d S rC   )rv   rA   fnr!   r"   inner   s    z DebugContext.wrap.<locals>.innerinductor)Zcompiler_name)	functoolswrapsr
   )rx   ry   r!   rw   r"   wrap   s    zDebugContext.wrapc                 C   sJ   t jD ]>}tjt d|  d| }tj|st| |  S qd S )Nr]   .)rv   _counterr_   rh   ri   r   rj   rk   )Zfolder_namendirnamer!   r!   r"   create_debug_dir   s    

zDebugContext.create_debug_dirc                 C   s   d | _ d | _t | _d S rC   )_prof_pathrd   re   _stack)selfr!   r!   r"   __init__   s    zDebugContext.__init__)new_pathc                 C   st   | j s
d S |dst|tj|r2t| zt| j | || _ W n$ t	k
rn   t
d| j | Y nX d S )Nz.debugz(Failed to copy debug files from %s to %s)r   endswithAssertionErrorr_   rh   rj   shutilrmtreecopytreeOSErrorr%   r&   )r   r   r!   r!   r"   copy   s    

  zDebugContext.copyc                 C   s    | j s
tttj| j |dS )Nw)r   r   openr_   rh   ri   r   filenamer!   r!   r"   fopen  s    
zDebugContext.fopenc                 C   s   t j| j|S rC   )r_   rh   ri   r   )r   suffixr!   r!   r"   r     s    zDebugContext.filenamec              	   C   s   t jjd k	r|dd l}| jsttj| jtj	| j d}|
|d }|j| jtj	| jd W 5 Q R X t j| d S )Nr   z.tar.gzzw:gz)arcname)r   trace
upload_tartarfiler   r   r_   rh   ri   basenamer   add)r   r   Ztar_filetarr!   r!   r"   r     s    
 $zDebugContext.upload_tarc                    s   t jr<td  j} tj  fdd}| j|| | j	t
|  t jjsZd S | t | _t jjr~| dtj t jjr| dtj t jjrt | _| j  d S )Nztorch._dynamoc                    s     |  d S rC   )rm   )levelr%   r!   r"   reset_log_level!  s    z/DebugContext.__enter__.<locals>.reset_log_levelz	debug.logzinfo.log)r   debugrb   rc   r   rm   rn   r   callbackrg   r   Zset_debug_handlerr   enabledr   r   r   	debug_log_setup_log_captureZinfo_logINFOZcompile_profilecProfileZProfiler   enable)r   Z
prev_levelr   r!   r   r"   	__enter__  s"    

zDebugContext.__enter__c                 C   sp   t d}| j| |}t |}|| |t d |	| |t
|j| | j|j| d S )Nztorch._inductorr^   )rb   rc   r   rg   r   StreamHandlerrm   ro   rp   rq   minr   r   rr   )r   r   r   r%   fdchr!   r!   r"   r   5  s    



zDebugContext._setup_log_capturec                 C   sF   | j r| j   |   | jr8|   tdt | j | j	  d S )Nz%s debug trace: %s)
r   disable_save_profile_datar   r   r%   r&   r   r   rf   )r   exc_typeexc_valexc_tbr!   r!   r"   __exit__A  s    
zDebugContext.__exit__c              	   C   sl   | j | d | dF}tj| j |d}|  |d |d |d |d W 5 Q R X d S )Nzcompile.profzcompile.stats)streamZcumtimed   Ztottime)	r   Z
dump_statsr   r   pstatsZStatsZ
strip_dirsZ
sort_statsZprint_stats)r   r   statsr!   r!   r"   r   K  s    


zDebugContext._save_profile_datac                 C   sZ   t jjrJtt j|rJztt| |W S  tk
rF   tjddd Y qVX ndd }|S d S )Nz Ignoring exception in debug codeT)exc_infoc                  _   s   d S rC   r!   rA   r!   r!   r"   ignored]  s    z)DebugContext.__getattr__.<locals>.ignored)r   r   r   getattrDebugFormatter	Exceptionr%   r&   )r   r;   r   r!   r!   r"   __getattr__U  s    zDebugContext.__getattr__N)r:   
__module____qualname__	itertoolscountr   staticmethodr}   r   r   strr   r   r   r   r   r   r   r   r   r!   r!   r!   r"   rv      s   



rv   c                   @   s   e Zd Zdd Zejjeej dddZ	ejjeej dddZ
edd	d
ZedddZeedddZedddZdd ZdS )r   c                 C   s   |j | _ |j| _|| _d S rC   )r   r   handler)r   r   r!   r!   r"   r   g  s    zDebugFormatter.__init__)r4   inputsc              	   C   sP   |  d}t|||d W 5 Q R X |  d}||jdd W 5 Q R X d S )Nzfx_graph_runnable.pyrz   zfx_graph_readable.pyFZprint_output)r   r	   writeprint_readabler   r4   r   r   r!   r!   r"   fx_graphl  s    zDebugFormatter.fx_graphc              	   C   s,   |  d}||jdd W 5 Q R X d S )Nzfx_graph_transformed.pyFr   )r   r   r   r   r!   r!   r"   fx_graph_transformeds  s    z#DebugFormatter.fx_graph_transformed)r(   c                 C   s   |  d| d S )Nzir_pre_fusion.txt	_write_irr   r(   r!   r!   r"   ir_pre_fusiony  s    zDebugFormatter.ir_pre_fusionc                 C   s   |  d| d S )Nzir_post_fusion.txtr   r   r!   r!   r"   ir_post_fusion|  s    zDebugFormatter.ir_post_fusion)r   r(   c              	   C   s<   |  |(}|D ]}||  |d qW 5 Q R X d S )Nz


)r   r   Z	debug_str)r   r   r(   r   r2   r!   r!   r"   r     s    zDebugFormatter._write_irc                 C   s   t || dd d S )Nzgraph_diagram.svg)r1   )r5   r   r   r!   r!   r"   graph_diagram  s    zDebugFormatter.graph_diagramc                 C   s   t || d d S )Nzoutput_code.py)r   r   r   r   r!   r!   r"   output_code  s    zDebugFormatter.output_codeN)r:   r   r   r   rM   r   r   r   Tensorr   r   SchedulerNodeListr   r   r   r   r   r   r!   r!   r!   r"   r   f  s    r   c                   @   s    e Zd ZU eed< ejed< dS )TensorMetadataHoldertensor_metadatadeviceN)r:   r   r   r   __annotations__rM   r   r!   r!   r!   r"   r     s   
r   c            
   	   O   s   d}t j|st | dd }t|| |f\}}d}| d| dtt d}t|d}t	||f| W 5 Q R X t
tjrd	| d
|d}	t|	 dS )z
    This function is used to save arguments for a compile_fx_inner function call
    to the file system.  Later on one can replay the compile_fx_inner call
    with the saved arguments using load_args_and_run_compile_fx_inner.
    z/tmp/inductor_saved_argsc                 S   s$   t | tjrtt| | jS | S dS )z
        Pickle FakeTensor will result in error:
        AttributeError: Can't pickle local object 'WeakValueDictionary.__init__.<locals>.remove'

        Convert all Tensor to metadata. This may also makes pickle faster.
        N)r+   rM   r   r   r   r   rE   r!   r!   r"   handle_tensor  s    z5save_args_for_compile_fx_inner.<locals>.handle_tensorcompile_fx_inner/_z.pklwbz3
Arguments for a compile_fx_inner call is saved to z. To replay the call,
run the following:

from torch._inductor.debug import load_args_and_run_compile_fx_inner
load_args_and_run_compile_fx_inner(z
)
        N)r_   rh   rj   mkdirr   nextsave_args_cntr   pickledumpr%   isEnabledForrb   rn   r/   )
r8   rB   folderr   Zargs_to_saveZkwargs_to_savefn_namerh   fmessager!   r!   r"   save_args_for_compile_fx_inner  s     
r   c                 C   s   ddl m} t| d}t|\}}W 5 Q R X dd }tjjdd}|N t	dd	6 t
|||f\}}|||W  5 Q R  W  5 Q R  S Q R X W 5 Q R X d S )
Nr   )r   rbc                 S   s4   t | tr,tjj| jj| jj| jj	| j
S | S d S rC   )r+   r   rM   Z_dynamotestingZrand_stridedr   shapeZstrider.   r   r   r!   r!   r"   r     s    
z9load_args_and_run_compile_fx_inner.<locals>.handle_tensorT)Zallow_non_fake_inputsZ	save_argsF)Ztorch._inductor.compile_fxr   r   r   loadrM   Z_subclassesZFakeTensorModer   r   r   )rh   r   r   r8   rB   r   Z	fake_moder!   r!   r"   "load_args_and_run_compile_fx_inner  s    r   )FN)DrK   rd   r   dataclassesr{   r   rb   r_   os.pathr   r   r   r   typingr   r   Zunittest.mockr   Zfunctorch.compiler   r   r   rM   r   Ztorch._dynamo.repro.after_aotr	   r
   Ztorch._dynamo.utilsr   Ztorch.fx.graph_moduler   Ztorch.fx.passes.shape_propr   r   Ztorch.fx.passes.tools_commonr   Ztorch.utils._pytreer    r   r   Z	schedulerr   r   r   r   r   Zvirtualizedr   rc   r:   r%   	lru_cacher#   r5   rN   r'   contextmanagerru   rv   r   r   	dataclassr   r   r   r   r   r!   r!   r!   r"   <module>   sT   


&Y
) &.