
    h                     Z    S SK Jr  S SKJr  S SKJr  S SKJr  \" \5      r	 " S S\5      r
g)    )	getLogger)Fusion)NumpyHelper)	OnnxModelc                   N   ^  \ rS rSrS\4U 4S jjrU 4S jrS rS rS r	Sr
U =r$ )	FusionConstantFold   modelc                 8   > [         TU ]  USS/5        SU l        g )N 	Transposer   )super__init__count)selfr
   	__class__s     g/var/www/fran/franai/venv/lib/python3.13/site-packages/onnxruntime/transformers/fusion_constant_fold.pyr   FusionConstantFold.__init__   s    [M2
    c                    > [         TU ]  5         U R                  S:  a#  [        R	                  SU R                   35        g g )Nr   zConstant Folded: )r   applyr   loggerinfo)r   r   s    r   r   FusionConstantFold.apply   s4    ::>KK+DJJ<89 r   c                 L    U R                  XU5        U R                  XU5        g)zH
Apply multiple fusions on Transpose nodes that can be constant folded.
N)fuse_1fuse_2)r   nodeinput_name_to_nodesoutput_name_to_nodes       r   fuseFusionConstantFold.fuse   s"     	D/BCD/BCr   c                    [        UR                  5      S:w  d  [        UR                  5      S:w  a  [        R	                  S5        gU R
                  R                  UR                  S   5      nUc  [        R	                  S5        gSnX!R                  S       H0  nUR                  S:X  a  [        UR                  5      S:X  a  M.  Sn  O   U(       a  [        R	                  S	5        gX!R                  S       H)  nUR                  S
:X  a  M  UR                  S:X  a  M'  Sn  O   U(       a  [        R	                  S5        g[        R                  " U5      n[        UR                  5      S:w  a  [        R	                  S5        gUR                  nUR                  n	U R                  U5        U R                  UU	UR                  S   UR                  S   /UR                  S9  X!R                  S       H  n[!        [        UR                  5      5       H  n
UR                  U
   UR                  S   :X  d  M%  UR                  S   UR                  U
'   UR                  S
:X  d  MS  U
S:X  d  U
S:X  d  Ma  U
S:X  a  SOSn[#        UR$                  5       H+  u  pUR                  U:X  d  M  SUR$                  U   l        M-     M     M     U R(                  R+                  U5        U =R,                  S-  sl        g)z
Constant fold any initializer data representing a MatMul's
weights that are stored in a Transpose op

Ex: Transpose --> Gemm or Transpose --> MatMul
   :fuse_constant_fold: node has more than one input or outputNr   z8fuse_constant_fold: failed to identify initializer inputFr   TzAfuse_constant_fold: other non-Transpose nodes use the initializerGemmMatMulzOfuse_constant_fold: other non-Gemm and non-MatMul nodes use the transposed data   z7fuse_constant_fold: shape of initializer data is not 2D)name	data_typedimsvalstransAtransB)leninputoutputr   debugr
   get_initializerop_typer   to_arrayshaper)   r*   remove_initializeradd_initializerTrange	enumerate	attributeinodes_to_removeappendr   )r   r   r   r    protoskip
child_nodeweightr)   dtyper=   keyjattr_keys                 r   r   FusionConstantFold.fuse_1    s~    tzz?a3t{{#3q#8LLUV 

**4::a=9=LLST -jjm<J&&+5#djj/Q:N = LL\] .kk!n=J&&&0J4F4F(4R > LLjk %%e,v||!LLRS zz&,,q/6<<?3	 	 	
 .kk!n=J3z//01##A&$++a.8*.**Q-J$$Q'!))V3a16*+q&hh+4Z5I5I+JKA'}}3<=
 4 4Q 7 9 ,K 2 > 	##D)

a
r   c                    [        UR                  5      S:w  d  [        UR                  5      S:w  a  [        R	                  S5        gU R
                  R                  USS5      nUc  [        R	                  S5        g[        UR                  5      S:w  d  [        UR                  5      S:w  a  [        R	                  S5        gUR                  S   R                  nUR                  S   R                  nXV:w  a  [        R	                  S5        gUR                  S   nX!R                  S      nU HC  n	[        U	R                  5       H'  u  pXR                  S   :X  d  M  XyR                  U
'   M)     ME     U R                  R                  U5        U R                  R                  U5        U =R                  S-  sl        g)	z
Constant fold any Transpose --> Transpose ops since the root input
is the final result

Ex: root_input --> Transpose --> Transpose --> next_node to root_input --> next_node
r$   r%   Nr   r   z<fuse_constant_fold: failed to identify parent Transpose nodezAfuse_constant_fold: parent node has more than one input or outputz@fuse_constant_fold: Transpose node permutations aren't identical)r/   r0   r1   r   r2   r
   match_parentr<   intsr;   r>   r?   r   )r   r   r   r    parent_node	node_permparent_node_perm
root_inputoutput_nodesoutput_noder=   input_s               r   r   FusionConstantFold.fuse_2h   sp    tzz?a3t{{#3q#8LLUV jj--dKCLLWX{  !Q&#k.@.@*AQ*FLL\]NN1%**	&00388(LL[\ !&&q)
*;;q>:'K&{'8'89	[[^++5%%a( : ( 	##D)##K0

a
r   )r   )__name__
__module____qualname____firstlineno__r   r   r   r!   r   r   __static_attributes____classcell__)r   s   @r   r   r      s+    i :
DFP( (r   r   N)loggingr   fusion_baser   fusion_utilsr   
onnx_modelr   rT   r   r    r   r   <module>r_      s+      $  	8	A Ar   