
    h3                    F    S SK Jr  S SKrSSKJr  SSKJr   " S S\5      rg)	    )annotationsN   )	ONNXModel   )Fusionc                  B   ^  \ rS rSrSU 4S jjr      SS jrSrU =r$ )FusionLayerNormalization   c                (   > [         TU ]  USS5        g )NLayerNormalization
ReduceMean)super__init__)selfmodel	__class__s     k/var/www/fran/franai/venv/lib/python3.13/site-packages/onnxruntime/quantization/fusions/fusion_layernorm.pyr   !FusionLayerNormalization.__init__   s     4lC    c                   U R                   R                  X5      n[        U5      S:X  d  [        U5      S:  a  gUR                  S   nUS   R                  S:w  d  US   R                  S   U:w  a  g[        U5      S:X  a*  US   R                  S:w  d  US   R                  S   U:w  a  gSnU H  nU R                  USUSS9nUc  M    O   Uc  gU R                  U/ S	Q/ S
Q4/ SQ/ SQ4/U5      u  pn
US:  a  gU	S   nX;  a  gU	S   nU R                  U5      u  pUb  US::  d  US:  a  gU	S   nU R                  US5      S:w  a  gX&R                  S      S   nUR                  S:w  a  gUUR                  S      S   nUR                  S:w  a  gU/nUR                  U5        UR                  U	SS 5        UR                  UUU/5        U R                  UUR                  UU5      (       d  gUR                  SU R                  UR                  S   U5      -
     nU R                  US5      (       d  gUR                  SU R                  UR                  S   U5      -
     nU R                  US5      (       d  gU R                  R                  U5        [        R                   R#                  SU R%                  5       UR                  S   UU/UR                  S   /S9nUR&                  R                  [        R                   R)                  S[+        U5      5      /5        U R,                  R/                  U5        g)au  
Interface function that tries to fuse a node sequence containing a ReduceMean node into a single
LayerNormalization node.

      +----------------------+
      |                      |
      |                      v
  [Root] --> ReduceMean -->  Sub  --> Pow --> ReduceMean --> Add --> Sqrt --> Div --> Mul --> Add
             (axis=2 or -1)  |      (Y=2)   (axis=2 or -1)  (E-6 or E-12 or 0) ^
                             |                                                 |
                             +-------------------------------------------------+

 It also handles cases of duplicated sub nodes exported from older version of PyTorch:

      +----------------------+
      |                      v
      |           +-------> Sub-----------------------------------------------+
      |           |                                                           |
      |           |                                                           v
  [Root] --> ReduceMean -->  Sub  --> Pow --> ReduceMean --> Add --> Sqrt --> Div  --> Mul --> Add
      |                      ^
      |                      |
      +----------------------+
r   r   NSubr   DivF)	recursive)SqrtAddr   Powr   )r   r   r   r   r   )r   r   r   r   Castr   )r   r   r   r   r   r   g-C6?   g       @Mulr   r   )nameinputsoutputsepsilon)r   get_childrenleninputop_typefind_first_child_by_typematch_parent_pathsget_constant_inputfind_constant_inputoutputextendis_safe_to_fuse_nodesinput_indexis_constant_with_specified_ranknodes_to_removeonnxhelper	make_nodecreate_unique_node_name	attributemake_attributefloatnodes_to_addappend)r   reduce_mean_nodeinput_name_to_nodesoutput_name_to_nodechildren
root_inputdiv_nodechildpath_idparent_nodes_sub_nodesecond_add_nodei
add_weightpow_nodemul_nodelast_add_nodesubgraph_nodesweight_input
bias_inputnormalize_nodes                         r   fuseFusionLayerNormalization.fuse   sj   < ::**+;Qx=AX!2%++A.
A;%'8A;+<+<Q+?:+Mx=A{""e+x{/@/@/Cz/QE44UECVbg4hH#  #'#:#:<oNG&  
$
 q Q;##&q///@qJ4G?##Hc2a7&q'9:1=u$+HOOA,>?B  E)*+h'l3B/0}hAB))  	
 
 ~~a$*:*:8??1;Mx*X&XY33L!DD"((T-=-=hooa>PR_-`)`a
33JBB##N3.. --/$**1-|ZH"))!,-	 / 
 	  '')C)CIuU_O`)a(bc  0r    )r   r   )r<   zonnx.NodeProtor=   zdict[str, list[onnx.NodeProto]]r>   zdict[str, onnx.NodeProto])__name__
__module____qualname____firstlineno__r   rQ   __static_attributes____classcell__)r   s   @r   r	   r	      s4    Du1(u1 =u1 7	u1 u1r   r	   )
__future__r   r3   
onnx_modelr   fusionr   r	   rS   r   r   <module>r]      s!    #  " y1v y1r   