U
    KcD                      @   s*  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 ddl	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mZmZmZmZmZ ddgZeeee ee ef Zeeee ee ee
f Ze jfddZdeeeej j!f eeef eeef ee ee ee eeef dddZ"dS )    N)GraphNode)Pattern   )QuantizeHandler   )
QConfigAny)MatchAllNode)is_observed_standalone_module)type_before_parametrizations)AnyDictListCallableOptionalTupleTypeSetis_matchfind_matchesc                    sj  t |tr4|^}}|tkr<t|dks.tdg }n|}g }t |trTt|trTdS t |trlt|j	|krpdS t |trt|t
jjr|jdkrdS t |j |ksdS n|t|r|jdks|j|k	rdS |jtkr|jd |d krdS n:t |tr|jdks|j|kr*dS n|j|kr*dS |s4dS t|t|jkrLdS t fd	d
t|j|D S )z, Matches a node in fx against a pattern
    r   z.Expecting getattr pattern to have two elementsTFcall_modulecall_functionr   Zcall_methodc                 3   s"   | ]\}}t  ||d dV  qdS )r   )max_usesN)r   ).0nodeZ	arg_matchmodules H/tmp/pip-unpacked-wheel-gikjz4vx/torch/ao/quantization/fx/match_utils.py	<genexpr>Q   s     zis_match.<locals>.<genexpr>)
isinstancetuplegetattrlenAssertionErrortype
issubclassr	   r   ZuserstorchnnModuleopr   targetcallableargsstrallzip)r   r   patternr   Z
self_matchZarg_matchesr   r   r   r   (   s@    


)graphr   patternsroot_node_getter_mappingstandalone_module_namesstandalone_module_classescustom_module_classesreturnc              	      s  |dkrg }dkrg dkr$g i }t  } fdd fddt| jD ]}	|	j|krP|	j|krP| D ]d\}
}||
d}t||	|
rp|	j|krpg }|
|	|	|| ||||}|	} |||||
|  qPqpqP|dk	st| jD ]<}	|	jdkrt	||	j
 |kr|	|	dt|	|ddf||	j< qttttjjf d	fd
d}| jD ]L}	|	jdkrP||	j
|s~t||	j
 rP|	|	dt|	|ddf||	j< qP|S )a  
    Matches the nodes in the input graph to quantization patterns, and
    outputs the information needed to quantize them in future steps.

    Inputs:
      - graph: an fx.Graph object
      - modules: a mapping of fully qualified module name to instance,
          for example, {'foo': ModuleFoo, ...}
      - patterns: a mapping from a tuple of nodes in reverse order to
          uninitialized QuantizeHandler subclass.

    Outputs a map of
      node_name ->
        (node, matched_values, matched_pattern, QuantizeHandler instance,
         qconfig)

    For example, {
      'relu_1': (relu_1, [relu_1], torch.nn.functional.relu,
                 <CopyNodeQuantizeHandler instance>, QConfig(...)),
      ...
    }
    Nc                    s>   t |tr| |||f||j< n|D ]} | ||||| q"d S N)r    r   name)	last_node	match_mapZnode_patternmatched_node_patternr1   Zmatch_valuen)#_recursive_record_node_in_match_mapr   r   r?   }   s    
   z9find_matches.<locals>._recursive_record_node_in_match_mapc           
         s   t | tr| ^}}g } ||||| | d tk	rXt||jD ]\}}	 ||	||| q>t|dkrt|t| q||d  n
|| d S )Nr   r   )r    r!   r"   r0   r-   r#   append)
r1   r   r;   r=   r<   sr-   Zcurrent_node_pattern
subpatternarg)record_matchr   r   rD      s.    
z"find_matches.<locals>.record_matchr   T)Zis_custom_moduleZnode_targetr   c                    s$   |d k	st | kp"t||   kS r9   )r$   r%   rE   )r6   r5   r   r   is_standalone_module   s    z*find_matches.<locals>.is_standalone_module)rF   )setreversedZnodesr:   itemsgetr   r$   r*   r%   r+   r   r.   r   r'   r(   r)   r
   )r2   r   r3   r4   r5   r6   r7   r<   Zall_matchedr   r1   Zquantize_handler_clsZroot_node_getterr=   Zquantize_handlerr;   rF   r   )r?   rD   r6   r5   r   r   S   sz    	

   "

  )NNN)#sysr'   Ztorch.fx.graphr   r   Z(torch.ao.quantization.quantization_typesr   Zquantization_patternsr   Zqconfigr   utilsr	   Zgraph_moduler
   Ztorch.nn.utils.parametrizer   typingr   r   r   r   r   r   r   r   __all__ZMatchResultZ_MatchResultWithQConfigmaxsizer   r.   r(   r)   r   r   r   r   r   <module>   s<   (0   

 
