§
    kŠtj£Â  ã                   óÒ   — d dl Z d dlZd dl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mZmZmZmZmZmZmZmZmZmZmZmZmZmZmZm Z  ddl!m"Z"  G d	„ d
e¦  «        Z#dS )é    N)Úonnx_pbé   )ÚBaseQuantizerÚQuantizationParams)Ú
TensorData)Ú	ONNXModel)ÚTENSOR_NAME_QUANT_SUFFIXÚQuantizationModeÚQuantizedValueÚQuantizedValueTypeÚ__producer__Ú__version__Úadd_infer_metadataÚattribute_to_kwargÚcompute_scale_zpÚcompute_scale_zp_float8Úfind_by_nameÚget_qmin_qmax_for_qTypeÚget_qrange_for_qTypeÚ	ms_domainÚquantize_onnx_initializerÚ&save_and_reload_model_with_shape_inferÚsnap_zero_point_to_uint8Útensor_proto_to_array)ÚCreateOpQuantizerc                   ó^  — e Zd Z	 d*d„Zd„ Zd„ Zd„ Zd„ Zd„ Zd„ Z	d	„ Z
d+d„Zd„ Zd„ Zd„ Zd„ Zd,d„Z	 d-d„Zd„ Z	 d*d„Zdej        dej        dedej        dedeeej        dz  f         fd„Zdedej        ddfd„Zd.d„Zd„ Zd+d „Z	 	 	 	 d/d"„Z 	 	 	 	 	 d0d$„Z!d1d%„Z"	 	 d2d&„Z#d'„ Z$d(„ Z%d)„ Z&dS )3ÚONNXQuantizerNc                 ó´  — t          j        | |||||||	|
||¦  «         |s½| j                             ¦   «          t	          | j        j        ¦  «        }d„ |j        j        D ¦   «         | _        | j                             d„ |j        j	        D ¦   «         ¦  «         | j                             d„ |j        j
        D ¦   «         ¦  «         t          |¦  «        | _        || _        || _        | j        dk    | _        d| j        v o| j        d         | _        g | _        d| _        i | _        | j                             d„ |j        j	        D ¦   «         ¦  «         | j                             d„ |j        j
        D ¦   «         ¦  «         | j        j        j        j        D ]:}| j                             t,                               |j	        d	¦  «        ¦  «         Œ;| j        t0          vrt3          d
| j        › �¦  «        ‚|                      ¦   «         | _        d| _        d| _        d| _        d| _        i | _         | j         !                    ¦   «         | _"        d S )Nc                 ó   — i | ]
}|j         |“ŒS © ©Úname)Ú.0Úvis     úe/var/www/html/CA-Chatbot/venv/lib/python3.11/site-packages/onnxruntime/quantization/onnx_quantizer.pyú
<dictcomp>z*ONNXQuantizer.__init__.<locals>.<dictcomp>I   s   € ÐMÐMÐM° ¤¨ÐMÐMÐMó    c                 ó   — i | ]
}|j         |“ŒS r    r!   ©r#   Úots     r%   r&   z*ONNXQuantizer.__init__.<locals>.<dictcomp>J   s   € Ð$NÐ$NÐ$N°R R¤W¨bÐ$NÐ$NÐ$Nr'   c                 ó   — i | ]
}|j         |“ŒS r    r!   ©r#   Úits     r%   r&   z*ONNXQuantizer.__init__.<locals>.<dictcomp>K   s   € Ð$MÐ$MÐ$M°R R¤W¨bÐ$MÐ$MÐ$Mr'   é
   ÚMatMulConstBOnlyú/c                 ó   — i | ]
}|j         d “ŒS ©r   r!   r)   s     r%   r&   z*ONNXQuantizer.__init__.<locals>.<dictcomp>W   s   € Ð!JÐ!JÐ!J° "¤'¨1Ð!JÐ!JÐ!Jr'   c                 ó   — i | ]
}|j         d “ŒS r2   r!   r,   s     r%   r&   z*ONNXQuantizer.__init__.<locals>.<dictcomp>X   s   € Ð!IÐ!IÐ!I° "¤'¨1Ð!IÐ!IÐ!Ir'   r   zunsupported quantization mode Úfixed_quantization_range_uint8Úfixed_quantization_range_int8Ú
fixed_zeroÚfixed_zero_zp)#r   Ú__init__ÚmodelÚreplace_gemm_with_matmulr   ÚgraphÚ
value_infoÚvalue_infosÚupdateÚoutputÚinputr   ÚmodeÚstaticÚopset_versionÚfuse_dynamic_quantÚextra_optionsÚq_matmul_const_b_onlyÚ	new_nodesÚgraph_scopeÚtensor_namesÚnodeÚdictÚfromkeysr
   Ú
ValueErrorÚcalculate_quantization_paramsÚquantization_paramsÚfixed_qrange_uint8_nameÚfixed_qrange_int8_nameÚfixed_zero_nameÚfixed_zero_zp_nameÚquantized_value_mapÚget_non_initializer_inputsÚgenerated_value_names)Úselfr9   Úper_channelÚreduce_rangerA   rB   Úweight_qTypeÚactivation_qTypeÚtensors_rangeÚnodes_to_quantizeÚnodes_to_excludeÚop_types_to_quantizerE   rJ   s                 r%   r8   zONNXQuantizer.__init__(   s`  € õ 	ÔØØØØØØØØØØ Øñ	
ô 	
ð 	
ð ð 	*ØŒJ×/Ò/Ñ1Ô1Ð1å:¸4¼:Ô;KÑLÔLˆEØMÐM°e´kÔ6LÐMÑMÔMˆDÔØÔ×#Ò#Ð$NÐ$N¸5¼;Ô;MÐ$NÑ$NÔ$NÑOÔOÐOØÔ×#Ò#Ð$MÐ$M¸5¼;Ô;LÐ$MÑ$MÔ$MÑNÔNÐNÝ" 5Ñ)Ô)ˆDŒJàˆŒ	ØˆŒØ"&Ô"4°rÒ"9ˆÔà%7¸4Ô;MÐ%MÐ%xÐRVÔRdÐewÔRxˆÔ"àˆŒØˆÔØˆÔØÔ× Ò Ð!JÐ!J°u´{Ô7IÐ!JÑ!JÔ!JÑKÔKÐKØÔ× Ò Ð!IÐ!I°u´{Ô7HÐ!IÑ!IÔ!IÑJÔJÐJØ”JÔ$Ô*Ô/ð 	Dð 	DˆDØÔ×$Ò$¥T§]¢]°4´;ÀÑ%BÔ%BÑCÔCÐCÐCàŒ9Õ,Ð,Ð,ÝÐI¸d¼iÐIÐIÑJÔJÐJà#'×#EÒ#EÑ#GÔ#GˆÔ ð (HˆÔ$Ø&EˆÔ#à+ˆÔà"1ˆÔð $&ˆÔ ð &*¤Z×%JÒ%JÑ%LÔ%LˆÔ"Ð"Ð"r'   c                 óž  — t           j                             |d| j        j        j        ¬¦  «        }t          |¦  «         t          || j        | j        | j	        | j
        | j        | j        | j        | j        | j        | j        | j        ¦  «        }| |_        | j        › |› d�|_        |                     ¦   «          |j        j        j        S )z¾
        generate submodel for the subgraph, so that we re-utilize current quantization implementation.
        quantize the submodel
        update subgraph and set it back to node
        úonnx-quantizer)Úproducer_nameÚopset_importsr0   )ÚonnxÚhelperÚ
make_modelr9   Úopset_importr   r   rX   rY   rA   rB   rZ   r[   r\   r]   r^   r_   rE   ÚparentrH   Úquantize_modelr;   )rW   ÚsubgraphÚ	graph_keyÚwarped_modelÚsub_quantizers        r%   Úquantize_subgraphzONNXQuantizer.quantize_subgraphq   s×   € õ ”{×-Ò-ØØ*Øœ*Ô*Ô7ð .ñ 
ô 
ˆõ
 	˜<Ñ(Ô(Ð(Ý%ØØÔØÔØŒIØŒKØÔØÔ!ØÔØÔ"ØÔ!ØÔ%ØÔñ
ô 
ˆð  $ˆÔØ'+Ô'7Ð$E¸Ð$EÐ$EÐ$EˆÔ!Ø×$Ò$Ñ&Ô&Ð&ØÔ"Ô(Ô.Ð.r'   c                 óÚ  — d„ |j         D ¦   «         }t          |¦  «        dk    r|S |j        r|j        n|j        › dt          | j        ¦  «        › �}i }|j         D ]á}|j        t          j        j        k    r-|j        |  	                    |j
        |› d|j        › �¦  «        i}nƒ|j        t          j        j        k    rZg }|j        D ]F}|                     |  	                    ||› d|j        › dt          |¦  «        › �¦  «        g¦  «         ŒG|j        |i}nt          |¦  «        }|                     |¦  «         Œât          j        j        |j        |j        |j        fd|j        i|¤ŽS )z|
        Check subgraph, if any, quantize it and replace it.
        return new_nodes added for quantizing subgraph
        c                 óz   — g | ]8}|j         t          j        j        k    s|j         t          j        j        k    ¯6|‘Œ9S r    )Útyperd   ÚAttributeProtoÚGRAPHÚGRAPHS)r#   Úattrs     r%   ú
<listcomp>z>ONNXQuantizer.quantize_node_with_sub_graph.<locals>.<listcomp>•   sG   € ð 
ð 
ð 
àØŒy�DÔ/Ô5Ò5Ð5¸¼ÅdÔFYÔF`Ò9`Ð9`ð à9`Ð9`Ð9`r'   r   Ú_node_count_ú:r"   )Ú	attributeÚlenr"   Úop_typerG   rq   rd   rr   rs   rn   Úgrt   ÚgraphsÚextendr   r>   re   Ú	make_noder@   r?   )	rW   rJ   Úgraph_attrsÚ	node_nameÚkwargsru   ÚkvÚvaluerj   s	            r%   Úquantize_node_with_sub_graphz*ONNXQuantizer.quantize_node_with_sub_graph�   s¤  € ð

ð 
àœð
ñ 
ô 
ˆõ
 ˆ{ÑÔ˜qÒ Ð ØˆKØ!%¤Ðb�D”I�I°4´<Ð0bÐ0bÍSÐQUÔQ_ÑM`ÔM`Ð0bÐ0bˆ	ØˆØ”Nð 	ð 	ˆDØŒy�DÔ/Ô5Ò5Ð5Ø”i ×!7Ò!7¸¼À9Ð@ZÐ@ZÈtÌyÐ@ZÐ@ZÑ![Ô![Ð\��Ø”�dÔ1Ô8Ò8Ð8Ø�Ø $¤ð ð �HØ—L’Là ×2Ò2Ø (Ø#,Ð GÐ G¨t¬yÐ GÐ G½3¸u¹:¼:Ð GÐ Gñô ðñô ð ð ð ”i Ð'��å'¨Ñ-Ô-�Ø�MŠM˜"ÑÔÐÐÝŒ{Ô$ T¤\°4´:¸t¼{ÐeÐeÐQUÔQZÐeÐ^dÐeÐeÐer'   c                 ób   — t          d„ | j                             ¦   «         D ¦   «         ¦  «        S )zQ
        Detect if model already has QuantizeLinear or DequantizeLinear.
        c              3   óB   K  — | ]}|j         d k    p
|j         dk    V — ŒdS )ÚQuantizeLinearÚDequantizeLinearN)r{   ©r#   rJ   s     r%   ú	<genexpr>z.ONNXQuantizer.has_QDQ_nodes.<locals>.<genexpr>¶   sH   è è € ð 
ð 
ØW[ˆDŒLÐ,Ò,ÐR°´Ð@RÒ0Rð
ð 
ð 
ð 
ð 
ð 
r'   )Úanyr9   Únodes)rW   s    r%   Úhas_QDQ_nodeszONNXQuantizer.has_QDQ_nodes²   sA   € õ ð 
ð 
Ø_cÔ_i×_oÒ_oÑ_qÔ_qð
ñ 
ô 
ñ 
ô 
ð 	
r'   c                 óš   — t          || j                             ¦   «         ¦  «        �dS | j        �| j                             |¦  «        S dS )NTF)r   r9   Úinitializerrh   Úfind_initializer_in_path)rW   Úinitializer_names     r%   r‘   z&ONNXQuantizer.find_initializer_in_pathº   sJ   € ÝÐ(¨$¬*×*@Ò*@Ñ*BÔ*BÑCÔCÐOØ�4ØŒ;Ð"Ø”;×7Ò7Ð8HÑIÔIÐIØˆur'   c                 óŒ   — | j                              |¦  «         |D ]&}|j        D ]}| j                             |¦  «         ŒŒ'd S ©N)rG   r~   r?   rV   Úadd)rW   r�   rJ   Úoutput_names       r%   Úadd_new_nodeszONNXQuantizer.add_new_nodesÁ   sa   € ØŒ×Ò˜eÑ$Ô$Ð$Øð 	<ð 	<ˆDØ#œ{ð <ð <�ØÔ*×.Ò.¨{Ñ;Ô;Ð;Ð;ð<ð	<ð 	<r'   c                 ó¬  — |                       ¦   «         rt          j        d¦  «         | j                             ¦   «         D ]ª}| j        r|                      |¦  «        }t          | j        ¦  «        }t          | |¦  «        }| 
                    ¦   «          t          |t          | j        ¦  «        ¦  «        D ]1}| j        |         j        D ]}| j                             |¦  «         ŒŒ2Œ«|                      ¦   «          | j                             ¦   «                              d¦  «         | j                             ¦   «         j                             | j        ¦  «         | j        €N| j                             ¦   «         \  }}t          |¦  «        dk    rt-          dt/          |¦  «        z   ¦  «        ‚t0          | j        j        _        t4          | j        j        _        d„ | j        j        j        D ¦   «         }|sId„ | j        D ¦   «         }	|	r6| j        j        j                             ¦   «         }
d|
_        t<          |
_        | j        j        S )Nz‹Please check if the model is already quantized. Note you don't need to quantize a QAT model. OnnxRuntime support to run QAT model directly.rJ   r   z0Invalid model with unknown initializers/tensors.c                 ó2   — g | ]}|j         t          k    ¯|‘ŒS r    )Údomainr   )r#   Úopsets     r%   rv   z0ONNXQuantizer.quantize_model.<locals>.<listcomp>ê   s%   € ÐbÐbÐb˜eÈÌÕXaÒHaÐHa�EÐHaÐHaÐHar'   c                 ó(   — g | ]}|j         d k    ¯|‘ŒS )zcom.microsoft)rš   rŠ   s     r%   rv   z0ONNXQuantizer.quantize_model.<locals>.<listcomp>ì   s$   € ÐZÐZÐZ ¸4¼;È/Ò;YÐ;Y˜Ð;YÐ;YÐ;Yr'   r   ) rŽ   ÚloggingÚwarningr9   r�   Úenable_subgraph_quantizationr…   rz   rG   r   ÚquantizeÚranger?   rV   r•   Ú_dequantize_outputsr;   Ú
ClearFieldrJ   r~   rh   Úclean_initializersÚRuntimeErrorÚstrr   rb   r   Úproducer_versionrg   Úversionr   rš   )rW   rJ   Únumber_of_existing_new_nodesÚop_quantizerÚir–   Ú_Úinitializers_not_foundÚms_opsetÚms_nodesr›   s              r%   ri   zONNXQuantizer.quantize_modelÇ   sG  € Ø×ÒÑÔð 	ÝŒOðnñô ð ð
 ”J×$Ò$Ñ&Ô&ð 
	@ð 
	@ˆDàÔ0ð ?Ø×8Ò8¸Ñ>Ô>�å+.¨t¬~Ñ+>Ô+>Ð(Ý,¨T°4Ñ8Ô8ˆLØ×!Ò!Ñ#Ô#Ð#ÝÐ7½¸T¼^Ñ9LÔ9LÑMÔMð @ð @�Ø#'¤>°!Ô#4Ô#;ð @ð @�KØÔ.×2Ò2°;Ñ?Ô?Ð?Ð?ð@ð@ð 	× Ò Ñ"Ô"Ð"ð 	Œ
×ÒÑÔ×%Ò% fÑ-Ô-Ð-ØŒ
×ÒÑÔÔ×&Ò& t¤~Ñ6Ô6Ð6ð Œ;ÐØ(,¬
×(EÒ(EÑ(GÔ(GÑ%ˆAÐ%ÝÐ)Ñ*Ô*¨QÒ.Ð.Ý"Ð#UÕX[Ð\rÑXsÔXsÑ#sÑtÔtÐtå)5ˆŒ
ÔÔ&Ý,7ˆŒ
ÔÔ)àbÐb t¤zÔ'7Ô'DÐbÑbÔbˆØð 	)ØZÐZ¨¬ÐZÑZÔZˆHØð )Øœ
Ô(Ô5×9Ò9Ñ;Ô;�Ø !�”Ý(�”àŒzÔÐr'   c                 ó–   — d| j         v r.t          j        d|| j         d         ¦  «         | j         d         S t          d|›d�¦  «        ‚)NÚDefaultTensorTypezDget_tensor_type returns DefaultTensorType for tensor name %r, use %dz)Unable to find data type for weight_name=a7  . shape_inference failed to return a type probably this node is from a different domain or using an input produced by such an operator. This may happen if you quantize a model already quantized. You may use extra_options `DefaultTensorType` to indicate the default weight type, usually `onnx.TensorProto.FLOAT`.)rE   r�   Úinfor¥   ©rW   Útensor_names     r%   Ú_get_default_tensor_typez&ONNXQuantizer._get_default_tensor_typeô   ss   € Ø $Ô"4Ð4Ð4ÝŒLØVØØÔ"Ð#6Ô7ñô ð ð
 Ô%Ð&9Ô:Ð:ÝðJ¸ð Jð Jð Jñ
ô 
ð 	
r'   Fc                 óP  — t          || j                             ¦   «         ¦  «        }|�|j        S || j        v rd| j        |         }|j                             d¦  «        r=|r*|j        j        j        dk    r|  	                    |¦  «        S |j        j        j        S | j
        r| j        €|r|  	                    |¦  «        S d S | j                             |¦  «        }|�|S | j
        r%| j        r| j                             |¦  «        }|�|S |r|  	                    |¦  «        S d S )NÚtensor_typer   )r   r9   r�   Ú	data_typer=   rq   ÚHasFieldr·   Ú	elem_typerµ   rŸ   rh   Úis_valid_quantize_weightÚget_tensor_type)rW   r´   Ú	mandatoryÚweightr$   ÚotypeÚress          r%   r¼   zONNXQuantizer.get_tensor_type  sF  € Ý˜k¨4¬:×+AÒ+AÑ+CÔ+CÑDÔDˆØÐØÔ#Ð#Ø˜$Ô*Ð*Ð*ØÔ! +Ô.ˆBØŒw×Ò Ñ.Ô.ð 5Øð F ¤Ô!4Ô!>À!Ò!CÐ!CØ×8Ò8¸ÑEÔEÐEØ”wÔ*Ô4Ð4ØÔ1ð 	°t´{Ð7JØð BØ×4Ò4°[ÑAÔAÐAØ�4Ø”×4Ò4°[ÑAÔAˆØÐØˆLØÔ,ð 	°´ð 	Ø”+×-Ò-¨kÑ:Ô:ˆCØˆØ�
Øð 	>Ø×0Ò0°Ñ=Ô=Ð=Øˆtr'   c                 óè  — |                       |¦  «        r|                      |¦  «        S || j        v r~| j        |         }|j                             d¦  «        r5|j        j        j        t          j        j	        t          j        j
        fv rdS t          j        d|›d|j        › d�¦  «         dS | j        r!| j        r| j                             |¦  «        S t          j        d|›d�¦  «         dS )	Nr·   Tz<Inference failed or unsupported type to quantize for tensor z
, type is ú.Fz%Failed to infer data type of tensor: zS. Please add data type info for this tensor if your model has customized operators.)Úis_input_a_initializerr»   r=   rq   r¹   r·   rº   Ú
onnx_protoÚTensorProtoÚFLOATÚFLOAT16r�   rž   rŸ   rh   Úis_float_tensor)rW   r´   r$   s      r%   rÈ   zONNXQuantizer.is_float_tensor  s"  € Ø×&Ò& {Ñ3Ô3ð 	>Ø×0Ò0°Ñ=Ô=Ð=à˜$Ô*Ð*Ð*ØÔ! +Ô.ˆBØŒw×Ò Ñ.Ô.ð °2´7Ô3FÔ3PÝÔ&Ô,ÝÔ&Ô.ðUð 4ð 4ð �tÝŒOØrÈ{ÐrÐrÐhjÔhoÐrÐrÐrñô ð ð �5àÔ,ð 	<°´ð 	<Ø”;×.Ò.¨{Ñ;Ô;Ð;åŒð7°Kð 7ð 7ð 7ñ	
ô 	
ð 	
ð ˆur'   c                 óØ   — |t           j        j        k    r|                      |||¦  «        S |t           j        j        k    r|                      |||¦  «        S t          d|› d�¦  «        ‚)a”  
        Create nodes for dynamic quantization of input and add them to nodes_list.
            parameter input_name: Name of the input.
            parameter nodes_list: new nodes are appended to this list.
            parameter qType: type to quantize to.
            parameter initial_type: type to quantize from
            return: scale_name, zero_point_name, scale_shape, zero_point_shape.
        zUnexpected value for qType=rÂ   )rÄ   rÅ   ÚINT8Ú+_get_dynamic_input_quantization_params_int8ÚUINT8Ú,_get_dynamic_input_quantization_params_uint8rM   )rW   Ú
input_nameÚ
nodes_listÚqTypeÚinitial_types        r%   Ú&_get_dynamic_input_quantization_paramsz4ONNXQuantizer._get_dynamic_input_quantization_params7  st   € ð •JÔ*Ô/Ò/Ð/Ø×CÒCÀJÐPZÐ\hÑiÔiÐiØ•JÔ*Ô0Ò0Ð0Ø×DÒDÀZÐQ[Ð]iÑjÔjÐjÝÐ?°uÐ?Ð?Ð?Ñ@Ô@Ð@r'   c                 óö  — t           j        j        }|dz   }|dz   }t          j                             d|g|dz   g|d¬¦  «        }|                     |¦  «         |dz   }t          j                             d|g|dz   g|d¬¦  «        }	|                     |	¦  «         |d	z   }
t          j                             d
|j        d         g|
dz   g|
¦  «        }|                     |¦  «         |d	z   }t          j                             d
|	j        d         g|dz   g|¦  «        }|                     |¦  «         |dz   }t          j                             d|j        d         |j        d         g|dz   g|¦  «        }|                     |¦  «         t          j                             | j	        |g t          |¦  «        dz  g¦  «        }| j                             |¦  «         |dz   }t          j                             d|j        d         | j	        g|g|¦  «        }|                     |¦  «         t          j                             | j        |g dg¦  «        }| j                             |¦  «         || j        g g fS )az  
        Create nodes for dynamic quantization of input to int8 and add them to nodes_list
            parameter input_name: Name of the input.
            parameter nodes_list: new nodes are appended to this list.
            parameter initial_type: initial weight type (FLOAT or FLOAT16)
            return: scale_name, zero_point_name, scale_shape, zero_point_shape.
        Ú_scaleÚ
_ReduceMinÚ	ReduceMinú:0r   ©ÚkeepdimsÚ
_ReduceMaxÚ	ReduceMaxÚ_AbsÚAbsÚ_Abs_MaxÚMaxç       @Ú	scale_DivÚDiv)rÄ   rÅ   rÊ   rd   re   r   Úappendr?   Úmake_tensorrQ   r   r9   Úadd_initializerrS   )rW   rÎ   rÏ   rÑ   rÐ   Úinput_scale_nameÚreduce_min_nameÚreduce_min_nodeÚreduce_max_nameÚreduce_max_nodeÚreduce_min_abs_nameÚreduce_min_abs_nodeÚreduce_max_abs_nameÚreduce_max_abs_nodeÚabs_max_nameÚabs_max_nodeÚinitializer_divÚscale_div_nameÚscale_div_nodeÚinitializer_zps                       r%   rË   z9ONNXQuantizer._get_dynamic_input_quantization_params_int8F  sÌ  € õ Ô&Ô+ˆð &¨Ñ0Ðà$ |Ñ3ˆÝœ+×/Ò/ØØˆLØ˜tÑ#Ð$ØØð 0ñ 
ô 
ˆð 	×Ò˜/Ñ*Ô*Ð*à$ |Ñ3ˆÝœ+×/Ò/ØØˆLØ˜tÑ#Ð$ØØð 0ñ 
ô 
ˆð 	×Ò˜/Ñ*Ô*Ð*ð .°Ñ6ÐÝ"œk×3Ò3ØØÔ# AÔ&Ð'Ø  4Ñ'Ð(Øñ	
ô 
Ðð 	×ÒÐ-Ñ.Ô.Ð.à-°Ñ6ÐÝ"œk×3Ò3ØØÔ# AÔ&Ð'Ø  4Ñ'Ð(Øñ	
ô 
Ðð 	×ÒÐ-Ñ.Ô.Ð.à! JÑ.ˆÝ”{×,Ò,ØØ Ô'¨Ô*Ð,?Ô,FÀqÔ,IÐJØ˜DÑ Ð!Øñ	
ô 
ˆð 	×Ò˜,Ñ'Ô'Ð'åœ+×1Ò1ØÔ'ØØÝ! %Ñ(Ô(¨3Ñ.Ð/ñ	
ô 
ˆð 	Œ
×"Ò" ?Ñ3Ô3Ð3Ø# kÑ1ˆÝœ×.Ò.ØØÔ  Ô# TÔ%@ÐAØÐØñ	
ô 
ˆð 	×Ò˜.Ñ)Ô)Ð)õ œ×0Ò0°Ô1HÈ%ÐQSÐVWÐUXÑYÔYˆØŒ
×"Ò" >Ñ2Ô2Ð2à Ô!8¸"¸bÐ@Ð@r'   c                 ó  — t           j        j        }|dz   }|dz   }|dz   }t          j                             d|g|dz   g|d¬¦  «        }|                     |¦  «         |dz   }	t          j                             d	|g|	dz   g|	d¬¦  «        }
|                     |
¦  «         t          j                             | j        |g t          |¦  «        g¦  «        }| j
                             |¦  «         t          j                             | j        |g d
g¦  «        }| j
                             |¦  «         |dz   }t          j                             d|
j        d         |j        d         g|dz   g|¦  «        }|                     |¦  «         |dz   }t          j                             d|j        d         | j        g|g|¦  «        }|                     |¦  «         |dz   }t          j                             d| j        |j        d         g|dz   g|¦  «        }|                     |¦  «         |dz   }t          j                             d|j        d         |g|dz   g|¦  «        }|                     |¦  «         |dz   }t          j                             d|j        |dz   g|¦  «        }|                     |¦  «         |dz   }t          j                             d|j        |g||¬¦  «        }|                     |¦  «         ||g g fS )a{  
        Create nodes for dynamic quantization of input to uint8 and add them to nodes_list
            parameter input_name: Name of the input.
            parameter nodes_list: new nodes are appended to this list.
            parameter initial_type: initial weight type (FLAOT or FLOAT16)
            return: scale_name, zero_point_name, scale_shape, zero_point_shape.
        rÔ   Ú_zero_pointrÕ   rÖ   r×   r   rØ   rÚ   rÛ   ç        Ú
_scale_SubÚSubÚ
_scale_Divrâ   Ú_zero_point_SubÚ_zero_point_DivÚ_zero_point_FloorÚFloorÚ_zero_point_CastÚCast)Úto)rÄ   rÅ   rÌ   rd   re   r   rã   rä   rP   r   r9   rå   rR   r?   )rW   rÎ   rÏ   rÑ   rÐ   ræ   Úinput_zp_namerç   rè   ré   rê   Úinitializer_qrangeÚinitializer_qvalueÚscale_sub_nameÚscale_sub_noderò   ró   Úzp_sub_nameÚzp_sub_nodeÚzp_div_nameÚzp_div_nodeÚzp_floor_nameÚzp_floor_nodeÚzp_cast_nameÚzp_cast_nodes                            r%   rÍ   z:ONNXQuantizer._get_dynamic_input_quantization_params_uint8š  sb  € õ Ô&Ô,ˆà%¨Ñ0ÐØ" ]Ñ2ˆà$ |Ñ3ˆÝœ+×/Ò/ØØˆLØ˜tÑ#Ð$ØØð 0ñ 
ô 
ˆð 	×Ò˜/Ñ*Ô*Ð*à$ |Ñ3ˆÝœ+×/Ò/ØØˆLØ˜tÑ#Ð$ØØð 0ñ 
ô 
ˆð 	×Ò˜/Ñ*Ô*Ð*õ "œ[×4Ò4ØÔ(ØØÝ! %Ñ(Ô(Ð)ñ	
ô 
Ðð 	Œ
×"Ò"Ð#5Ñ6Ô6Ð6Ý!œ[×4Ò4°TÔ5IÈ<ÐY[Ð^aÐ]bÑcÔcÐØŒ
×"Ò"Ð#5Ñ6Ô6Ð6ð $ lÑ2ˆÝœ×.Ò.ØØÔ# AÔ&¨Ô(>¸qÔ(AÐBØ˜dÑ"Ð#Øñ	
ô 
ˆð 	×Ò˜.Ñ)Ô)Ð)à# lÑ2ˆÝœ×.Ò.ØØÔ" 1Ô% tÔ'CÐDØÐØñ	
ô 
ˆð 	×Ò˜.Ñ)Ô)Ð)ð !Ð#4Ñ4ˆÝ”k×+Ò+ØØÔ! ?Ô#9¸!Ô#<Ð=Ø˜4ÑÐ Øñ	
ô 
ˆð 	×Ò˜+Ñ&Ô&Ð&à Ð#4Ñ4ˆÝ”k×+Ò+ØØÔ Ô"Ð$4Ð5Ø˜4ÑÐ Øñ	
ô 
ˆð 	×Ò˜+Ñ&Ô&Ð&à"Ð%8Ñ8ˆÝœ×-Ò-¨g°{Ô7IÈMÐ\`ÑL`ÐKaÐcpÑqÔqˆØ×Ò˜-Ñ(Ô(Ð(à!Ð$6Ñ6ˆÝ”{×,Ò,¨V°]Ô5IÈMÈ?Ð\hÐmrÐ,ÑsÔsˆØ×Ò˜,Ñ'Ô'Ð'à °°BÐ6Ð6r'   c                 ó"  — | j         }|�|�€R| j        �	|| j        vrt          j        d|› d�¦  «         dS | j        |         }t	          |t
          ¦  «        s#t          dt          |¦  «        › d|›d�¦  «        ‚|�t          |¦  «        dk    rt          d	|› d
|› �¦  «        ‚t          j        |d         g¦  «        }t          |d         d¦  «        r%|d         j        t          j        t          j        fvr(t          dt          |d         ¦  «        › d|›�¦  «        ‚t          j        |d         g¦  «        }|j        t          j        k    sJ ‚|d         }ntt          j        |g¦  «        }t          j        |g¦  «        }| j        |         }d|v r"|d         j        }|                     |¦  «        }|j        t          j        k    sJ ‚g }	|dz   }
g }|dz   }t$          j                             |
||	|                     ¦   «                              ¦   «         ¦  «        }| j                             |¦  «         |j        t          j        k    rt2          j        j        }nA|j        t          j        k    rt2          j        j        }nt          d|j        › d|›�¦  «        ‚t$          j                             ||||                     d¦  «                             ¦   «         ¦  «        }| j                             |¦  «         d||
||	fS )a\  
        Create initializers and inputs in the graph for zero point and scale of output.
        Zero point and scale values are obtained from self.quantization_params if specified.
            parameter param_name: Name of the quantization parameter.
            return: result, scale_name, zero_point_name, scale_shape, zero_point_shape.
        Nz$Quantization parameters for tensor:"z" not specified)FÚ r  r  r  úUnexpected type ú for rÂ   é   zbQuantization parameters should contain zero point, scale, quant type. Specified values for output z: Ú
zero_pointÚscaleÚdtypez and param_name=Ú
quant_typerö   rÔ   zUnexpected dtype=z for param_name=)éÿÿÿÿT)r[   rO   r�   r²   Ú
isinstancer   Ú	TypeErrorrq   rz   rM   ÚnpÚarrayÚhasattrr  Úfloat32Úfloat16Úfloat64Úastyperd   re   rä   ÚravelÚtolistr9   rå   rÄ   rÅ   rÆ   rÇ   Úreshape)rW   Ú
param_nameÚ	use_scaleÚuse_zeropointÚzero_point_typeÚparamsÚzero_point_valuesÚscale_valuesr  Úzero_point_shapeÚzero_point_nameÚscale_shapeÚ
scale_nameÚinit_zpÚ
scale_typeÚ
init_scales                   r%   Ú_get_quantization_paramsz&ONNXQuantizer._get_quantization_paramsø  s5  € ð Ô/ˆàÐ Ñ 5ØÔ'Ð/°:ÀTÔE]Ð3]Ð3]Ý”Ð_ÀJÐ_Ð_Ð_Ñ`Ô`Ð`Ø,Ð,àÔ-¨jÔ9ˆFÝ˜fÕ&8Ñ9Ô9ð WÝÐ Uµ4¸±<´<Ð UÐ UÀjÐ UÐ UÐ UÑVÔVÐVØˆ~¥ V¡¤°Ò!1Ð!1Ý ðJØ3=ðJð JØAGðJð Jñô ð õ
 !#¤¨&°Ô*>Ð)?Ñ @Ô @ÐÝ˜6 'œ?¨GÑ4Ô4ð k¸¸w¼Ô8MÕVXÔV`ÕbdÔblÐUmÐ8mÐ8mÝ Ð!iµD¸À¼Ñ4IÔ4IÐ!iÐ!iÐ[eÐ!iÐ!iÑjÔjÐjÝœ8 V¨G¤_Ð$5Ñ6Ô6ˆLØÔ%­¬Ò3Ð3Ð3Ð3Ø$ \Ô2ˆOˆOå "¤¨-¨Ñ 9Ô 9ÐÝœ8 Y KÑ0Ô0ˆLØÔ-¨jÔ9ˆFØ˜&Ð Ð Ø˜wœÔ-�Ø+×2Ò2°5Ñ9Ô9�ØÔ%­¬Ò3Ð3Ð3Ð3àÐØ$ }Ñ4ˆØˆØ (Ñ*ˆ
õ ”+×)Ò)Ø˜_Ð.>Ð@Q×@WÒ@WÑ@YÔ@Y×@`Ò@`Ñ@bÔ@bñ
ô 
ˆð 	Œ
×"Ò" 7Ñ+Ô+Ð+ØÔ¥¤Ò+Ð+Ý#Ô/Ô5ˆJˆJØÔ¥2¤:Ò-Ð-Ý#Ô/Ô7ˆJˆJåÐc°Ô1CÐcÐcÐU_ÐcÐcÑdÔdÐdÝ”[×,Ò,¨Z¸À[ÐR^×RfÒRfÐglÑRmÔRm×RtÒRtÑRvÔRvÑwÔwˆ
ØŒ
×"Ò" :Ñ.Ô.Ð.à�Z °+Ð?OÐOÐOr'   c           	      ó¢  — |j         |         }|dk    s
J d¦   «         ‚|t          z   }|dz   }	|�	|�d||}}}
n|                      |¦  «        \  }
}}}}g }|
r't          j                             d|||g|g|	¦  «        }n²| j        rdS | j        rF|t          j	        j
        k    r1|dz   }|dz   }t          j                             d	|g|||g|	¦  «        }n\|€J d
|›d|› d|› d|› �¦   «         ‚|                      ||||¬¦  «        \  }}}}t          j                             d|||g|g|	¦  «        }t          |||||¦  «        | j        |<   g |¢|‘S )aÊ  
        Given an input for a node (which is not a initializer), this function

        - add nodes to compute zero point and scale for this input if they don't exist.
        - add new QuantizeLinear node to quantize the input.

        :param node: node being quantized in NodeProto format.
        :param input_index: index of input in node.input.
        :param qType: type to quantize to.
        :param given_scale_name: if those inputs need to be quanitzed using this scale tensor.
        :param given_zp_name: if those inputs to be quantized using this zeropoint tensor.
        :param initial_type: type of the weight to quantize
        :return: List of newly created nodes in NodeProto format.
        r  z*Cannot access undefined variable in graph.Ú_QuantizeLinearNTrˆ   rÔ   rö   ÚDynamicQuantizeLinearzCCannot quantize input without knowing the initial type, input_name=z, input_index=z, qType=z, node=©rÑ   )r@   r	   r3  rd   re   r   rB   rD   rÄ   rÅ   rÌ   rÒ   r   rT   )rW   rJ   Úinput_indexrÐ   Úgiven_scale_nameÚgiven_zp_namerÑ   rÎ   r–   Úql_node_nameÚ
data_foundr/  Úzp_namer¬   r�   Úqlinear_noder.  Úzp_shapes                     r%   Ú_get_quantize_input_nodesz'ONNXQuantizer._get_quantize_input_nodes3  s
  € ð" ”Z Ô,ˆ
Ø˜RÒÐÐÐ!MÑÔÐØ Õ#;Ñ;ˆØ!Ð$5Ñ5ˆàÐ(¨}Ð/HØ/3Ð5EÀ} G˜
ˆJˆJà48×4QÒ4QÐR\Ñ4]Ô4]Ñ1ˆJ˜
 G¨Q°àˆØð %	Ýœ;×0Ò0Ø Ø˜Z¨Ð1Ø�Øñ	ô ˆLˆLð Œ{ð Ø�tð Ô&ð ¨5µJÔ4JÔ4PÒ+PÐ+PØ'¨(Ñ2�
Ø$ }Ñ4�Ý#œ{×4Ò4Ø+Ø�LØ  *¨gÐ6Ø ñ	 ô  ��ð $Ð/Ð/ðhØ",ðhð hØ>Iðhð hØSXðhð hØaeðhð hñ 0Ô/Ð/ð ×?Ò?À
ÈEÐSXÐgsÐ?ÑtÔtñØØØØå#œ{×4Ò4Ø$Ø ¨WÐ5Ø �MØ ñ	 ô  �õ 0>¸jÈ+ÐWaÐcjÐlqÑ/rÔ/rˆÔ  Ñ,Ø%�Ð%˜Ð%Ð%r'   c                 ót   — || j         v r| j         |         S | j        �| j                             |¦  «        S d S r”   )rT   rh   Úfind_quantized_value)rW   rÎ   s     r%   rB  z"ONNXQuantizer.find_quantized_valuey  sA   € Ø˜Ô1Ð1Ð1ØÔ+¨JÔ7Ð7ØŒ;Ð"Ø”;×3Ò3°JÑ?Ô?Ð?Øˆtr'   c
                 ó&  — t          j        |¦  «        }
|d|
z  z  |z  }t          j        |                     ¦   «         t           j        ¬¦  «        }t          j        |                     ¦   «         t           j        ¬¦  «        }||z  }||k     r€|dk    rz||z  }||z  }|	€6t          j        d|› d|› d|› d�¦  «         d	t          j        ||¬¦  «        fS t          j        d
|	› d|› d|› d|› d�	¦  «         d	|                     |¦  «        fS d|fS )zHAdjust a single weight scale to ensure the int32 bias does not overflow.rà   ©r  r÷   NzIncreasing scale for weight `z` by the ratio z to ensure bias `z` has a valid scale.TzIncreased scale[z] for weight `z` by ratio F)r  Úabsr  Úitemr   r�   r²   r!  )rW   Úbias_valÚinput_scaleÚweight_scaleÚweight_scale_dtypeÚweight_nameÚ	bias_nameÚqrangeÚmultiplicative_epsilonÚidxÚabsmaxÚbias_smallest_valid_scaleÚinput_scale_fp64Úweight_scale_fp64Úbias_candidate_scaleÚratioÚ	new_scales                    r%   Ú$adjust_single_weight_scale_if_neededz2ONNXQuantizer.adjust_single_weight_scale_if_needed€  s•  € õ ”˜Ñ!Ô!ˆØ$:¸cÀF¹lÑ$KÈfÑ$TÐ!åœ8 K×$4Ò$4Ñ$6Ô$6½b¼jÐIÑIÔIÐÝœH \×%6Ò%6Ñ%8Ô%8ÅÄ
ÐKÑKÔKÐØ/Ð2CÑCÐà Ð#<Ò<Ð<ÐCWÐZ]ÒC]ÐC]Ø-Ð0DÑDˆEØ)¨EÑ1ˆIØˆ{Ý”ðD°Kð Dð DÐPUð Dð DØ$-ðDð Dð Dñô ð ð �RœX iÐ7IÐJÑJÔJÐJÐJå”ðG sð Gð G¸+ð Gð GÐRWð Gð GØ'0ðGð Gð Gñô ð ð ˜Y×-Ò-Ð.@ÑAÔAÐAÐAØ�lÐ"Ð"r'   rH  rI  rK  Úbias_tpÚis_per_channelÚreturnc                 óö  — |j         sdS t          |¦  «        }t          j        t          j        ¦  «        }d}t          j        |j        t          j        ¬¦  «        t          j        |j        dz   t          j        ¬¦  «        z
  }	|j	        }
d}|sît          j
        |                     ¦   «         t          j        dt          j        ¬¦  «        ¦  «        }t          j        |                     ¦   «         t          j        dt          j        ¬¦  «        ¦  «        }t          j        t          j        |¦  «        t          j        |¦  «        ¦  «        }|                      ||||
||j        |	|¦  «        \  }}|r|}d}nw|j        rpt!          |j        ¦  «        dk    rXt#          |j        d         ¦  «        D ]=}|                      ||         |||         |
||j        |	||¬¦	  «	        \  }}|r|||<   d}Œ>||fS )	zOChecks if the bias scale is too small and increases the weight scale if needed.)FNgq¬‹Ûh ð?rD  r   Fr   T)rO  )Úsizer   r  ÚiinfoÚint32r  Úmaxr   Úminr  ÚminimumÚmaximumrE  rW  r"   Úshaperz   r¡   )rW   rH  rI  rK  rX  rY  Úbias_float_dataÚ
int32_inforN  rM  rJ  ÚupdatedÚrminÚrmaxrP  ÚchangedrV  r«   s                     r%   Ú#_adjust_weight_scale_for_int32_biasz1ONNXQuantizer._adjust_weight_scale_for_int32_bias¥  sõ  € ð Ô ð 	Ø�;å/°Ñ8Ô8ˆÝ”X�bœhÑ'Ô'ˆ
Ø!'ÐÝ”˜*œ.µ´
Ð;Ñ;Ô;½b¼hÀzÄ~ÐXYÑGYÕacÔakÐ>lÑ>lÔ>lÑlˆØ)Ô/ÐØˆàð  	#Ý”:˜o×1Ò1Ñ3Ô3µR´X¸aÅrÄzÐ5RÑ5RÔ5RÑSÔSˆDÝ”:˜o×1Ò1Ñ3Ô3µR´X¸aÅrÄzÐ5RÑ5RÔ5RÑSÔSˆDÝ”Z¥¤ t¡¤­b¬f°T©l¬lÑ;Ô;ˆFØ!%×!JÒ!JØØØØ"ØØ”ØØ&ñ	"ô 	"ÑˆG�Yð ð Ø(�Ø�øØÔð 	#¥C¨Ô(:Ñ$;Ô$;¸qÒ$@Ð$@Ý˜<Ô-¨aÔ0Ñ1Ô1ð #ð #�Ø%)×%NÒ%NØ# AÔ&ØØ  ”OØ&ØØ”LØØ*Øð &Oñ 
&ô 
&Ñ"�˜ð ð #Ø&/�L ‘OØ"�Gøà˜Ð$Ð$r'   rV  c                 óä  — || j         vrdS | j         |         }t          || j                             ¦   «         ¦  «        }t          |j        | j                             ¦   «         ¦  «        }t          |j        | j                             ¦   «         ¦  «        }t          |j        | j                             ¦   «         ¦  «        }|�|�|�|€dS | j                             |¦  «         | j                             |¦  «         t          j	         
                    |¦  «        }|j        }	t          j        |t          j                             |j        ¦  «        ¬¦  «        }
t          j	                             |
                     |j        ¦  «        |j        ¦  «        }| j                             |¦  «         t+          || j        ||
|	|j        ¬¦  «        }| j                             |¦  «         dS )zCRe-quantizes the given weight initializer using the provided scale.NrD  )Úquant_weight_name)rT   r   r9   r�   r/  r=  Úq_nameÚremove_initializerrd   Únumpy_helperÚto_arrayÚaxisr  Úasarrayre   Útensor_dtype_to_np_dtyper¸   Ú
from_arrayr$  Údimsrå   r   rZ   )rW   rK  rV  ÚqvÚ	weight_tpÚ
scale_initÚzp_initÚq_weight_initÚweight_zero_pointrq  Úscale_npÚnew_scale_initÚnew_q_weights                r%   Ú_requantize_weightz ONNXQuantizer._requantize_weightÝ  s¸  € ð ˜dÔ6Ð6Ð6ØˆFàÔ% kÔ2ˆå  ¨d¬j×.DÒ.DÑ.FÔ.FÑGÔGˆ	Ý! "¤-°´×1GÒ1GÑ1IÔ1IÑJÔJˆ
Ý˜rœz¨4¬:×+AÒ+AÑ+CÔ+CÑDÔDˆÝ$ R¤Y°´
×0FÒ0FÑ0HÔ0HÑIÔIˆàÐ 
Ð 2°g°oÈÐI^ØˆFàŒ
×%Ò% jÑ1Ô1Ð1ØŒ
×%Ò% mÑ4Ô4Ð4å Ô-×6Ò6°wÑ?Ô?ÐØŒwˆõ ”:˜i­t¬{×/SÒ/SÐT]ÔTgÑ/hÔ/hÐiÑiÔiˆÝÔ*×5Ò5°h×6FÒ6FÀzÄÑ6WÔ6WÐY[ÔYfÑgÔgˆØŒ
×"Ò" >Ñ2Ô2Ð2õ 1ØØÔØØØØ œið
ñ 
ô 
ˆð 	Œ
×"Ò" <Ñ0Ô0Ð0Ð0Ð0r'   ç      ð?c           
      ó�  — || j         v r| j         |         j        S | j         |         j        }t          || j                             ¦   «         ¦  «        }t          |¦  «        }|| j         v r| j         |         j        }n8|| j        v r|                      |¦  «        \  }	}}	}	}	nt          d|› d�¦  «        ‚t          || j                             ¦   «         ¦  «        }
t          |
¦  «        }| j         |         j
        }t          || j                             ¦   «         ¦  «        }|�t          j                             |¦  «        nd}| j        }|�‘|j        rŠ|                     ¦   «         sv| j        t$          j        j        fv r]t          || j                             ¦   «         ¦  «        }|                      |||||¦  «        \  }}|r|                      ||¦  «         |}|                      ||||¦  «        \  }}}}}}|| j         vsJ ‚t1          ||||t2          j        |j        dk    rdnd||¬¦  «        }|| j         |<   |S )z]
        Quantized the bias. Zero Point == 0 and Scale == Input_Scale * Weight_Scale
        z	Expected z5 to be in quantized value map for static quantizationNr   r   )Ú	node_typeÚ
node_qtype)rT   rm  r/  r   r9   r�   r   rO   r3  rM   r=  rd   ro  rp  rX   r\  rŒ   rZ   rÄ   rÅ   rÊ   rj  r  Úquantize_bias_static_implr   r   ÚInitializer)rW   rL  rÎ   rK  ÚbetaÚweight_scale_nameÚweight_initializerrI  ræ   r¬   Úinputscale_initializerrH  Úweight_zp_nameÚweight_zp_initr{  rY  Úbias_initializerÚ
did_updateÚnew_weight_scaleÚquantized_bias_nameÚquantized_bias_scale_nameÚquantized_bias_zp_nameÚbias_scale_datar‚  rƒ  Úquantized_values                             r%   Úquantize_bias_staticz"ONNXQuantizer.quantize_bias_static  sž  € ð ˜Ô0Ð0Ð0ØÔ+¨IÔ6Ô=Ð=ð !Ô4°[ÔAÔLÐÝ)Ð*;¸T¼Z×=SÒ=SÑ=UÔ=UÑVÔVÐÝ,Ð-?Ñ@Ô@ˆð ˜Ô1Ð1Ð1Ø#Ô7¸
ÔCÔNÐÐØ˜4Ô3Ð3Ð3Ø+/×+HÒ+HÈÑ+TÔ+TÑ(ˆAÐ  A q qåÐj¨ÐjÐjÐjÑkÔkÐkå!-Ð.>ÀÄ
×@VÒ@VÑ@XÔ@XÑ!YÔ!YÐÝ+Ð,BÑCÔCˆð Ô1°+Ô>ÔFˆÝ% n°d´j×6LÒ6LÑ6NÔ6NÑOÔOˆØJXÐJd�DÔ-×6Ò6°~ÑFÔFÐFÐjnÐØÔ)ˆàÐ)Ø!Ô&ð *à%×)Ò)Ñ+Ô+ð *ð Ô!¥jÔ&<Ô&AÐ%CÐCÐCå+¨I°t´z×7MÒ7MÑ7OÔ7OÑPÔPÐØ+/×+SÒ+SØØØØ Øñ,ô ,Ñ(ˆJÐ(ð ð 0Ø×'Ò'¨Ð5EÑFÔFÐFØ/�ð ×*Ò*¨9°kÀ<ÐQUÑVÔVñ	
ØØ%Ø"ØØØð  Ô 8Ð8Ð8Ð8Ð8Ý(ØØØ%Ø"ÝÔ*Ø Ô%¨Ò)Ð)ˆAˆA¨tØØ!ð	
ñ 	
ô 	
ˆð />ˆÔ  Ñ+à"Ð"r'   c                 ó8   — || j         v p|| j        v p|| j        v S )zq
        only check for value info and newly generated tensor names, initializers are checked separately
        )r=   rI   rV   r³   s     r%   Úcontains_tensorzONNXQuantizer.contains_tensorK  s4   € ð
 ˜DÔ,Ð,ð ;Ø˜tÔ0Ð0ð;à˜tÔ9Ð9ð	
r'   c           	      ó:   — |                       ||dddd|¬¦  «        S )NFr  ©rJ   ÚindicesÚinitializer_use_weight_qTyperY   Úop_level_per_channelrq  Úfrom_subgraph©Ú_ONNXQuantizer__quantize_inputs)rW   rJ   r™  rœ  s       r%   Úquantize_activationz!ONNXQuantizer.quantize_activationU  s4   € Ø×%Ò%ØØØ).ØØ!&ØØ'ð &ñ 
ô 
ð 	
r'   r  c           	      ó:   — |                       ||d||||¬¦  «        S )NTr˜  r�  )rW   rJ   r™  rY   r›  rq  rœ  s          r%   Úquantize_weightzONNXQuantizer.quantize_weightb  s6   € ð ×%Ò%ØØØ)-Ø%Ø!5ØØ'ð &ñ 
ô 
ð 	
r'   Tc           
      óŽ  — g }g }	g }
g }|D �]4}|j         |         }|| j        v r\| j        |         }|                     |j        ¦  «         |	                     |j        ¦  «         |
                     |j        ¦  «         Œu|s@|
                     d¦  «         |                     d¦  «         |	                     d¦  «         Œ·t          || j                             ¦   «         ¦  «        }|�£| j	        r2|r0|  
                    |j        |r| j        n| j        ||¦  «        \  }}}n)|                      ||r| j        n| j        |¦  «        \  }}}|
                     |¦  «         |	                     |¦  «         |                     |¦  «         �Œƒ|                      |¦  «        �r| j                             |dz   | j        | j                             ¦   «         ¦  «        }|€ü|j         |         }|| j        v rj| j        |         }|                     d¦  «        sJ d|› d�¦   «         ‚|j                             d¦  «        sJ d|› d�¦   «         ‚|j        j        j        }n$|| j        v sJ d	|›d
�¦   «         ‚| j        |         }|                      ||| j        |¬¦  «        }|€ dS |r|                      |¦  «         n|                     |¦  «         |d         }|j        dk    r\|
                     |j        ¦  «         |                     |j         d         ¦  «         |	                     |j         d         ¦  «         �Œ9|
                     |j        d         ¦  «         |                     |j        d         ¦  «         |	                     |j        d         ¦  «         �Œ›| j        �z| j                             ||g||||d¬¦  «        \  }}}}|
                     |d         ¦  «         |                     |d         ¦  «         |	                     |d         ¦  «         �ŒtA          d|› d| j!        › �¦  «        ‚|
|	||fS )a›  
        Given a node, this function quantizes the inputs as follows:
            - If input is an initializer, quantize the initializer data, replace old initializer
              with new initializer
            - Else, add QuantizeLinear nodes to perform quantization
            parameter node: node being quantized in NodeProto format.
            parameter indices: input indices to quantize.
            return: (List of quantized input names,
                     List of zero point names used for input quantization,
                     List of scale names used for input quantization,
                     List of new QuantizeLinear nodes created)
        r  Nr5  rq   zvalue_info=z has no type.r·   z is not a tensor.zshape inference failed for zF and attribute 'tensor_names' does not have any value for this tensor.r7  )NNNNr  rˆ   r   é   r   T)rš  rY   r›  rq  rœ  z!Invalid tensor name to quantize: z @graph scope)"r@   rT   rã   r/  r=  rm  r   r9   r�   rX   Úquantize_weight_per_channelr"   rZ   r[   Úquantize_initializerr–  Úfind_node_by_namerG   r;   r=   r¹   rq   r·   rº   rI   r@  r—   r~   r{   r?   rh   rž  rM   rH   )rW   rJ   r™  rš  rY   r›  rq  rœ  Úscale_namesÚzero_point_namesÚquantized_input_namesr�   r8  Ú
node_inputr“  r�   Úq_weight_namer=  r/  r>  rÎ   r<   rÑ   Úquantize_input_nodesÚparent_quantized_input_namesÚparent_zero_point_namesÚparent_scale_namesr¬   s                               r%   Ú__quantize_inputszONNXQuantizer.__quantize_inputsu  s  € ð. ˆØÐØ "ÐØˆà"ð c	rñ c	rˆKØœ KÔ0ˆJð ˜TÔ5Ð5Ð5Ø"&Ô":¸:Ô"F�Ø×"Ò" ?Ô#=Ñ>Ô>Ð>Ø ×'Ò'¨Ô(?Ñ@Ô@Ð@Ø%×,Ò,¨_Ô-CÑDÔDÐDØàð Ø%×,Ò,¨RÑ0Ô0Ð0Ø×"Ò" 2Ñ&Ô&Ð&Ø ×'Ò'¨Ñ+Ô+Ð+Øå& z°4´:×3IÒ3IÑ3KÔ3KÑLÔLˆKØÐ&ØÔ#ð Ð(<ð ð
 ×8Ò8Ø#Ô(Ø-IÐd˜Ô)Ð)ÈtÔOdØØ$ñ	ô ñ	Ø%ØØ"˜
ð :>×9RÒ9RØ#Ø-IÐd˜Ô)Ð)ÈtÔOdØ$ñ:ô :Ñ6�M 7¨Jð &×,Ò,¨]Ñ;Ô;Ð;Ø ×'Ò'¨Ñ0Ô0Ð0Ø×"Ò" :Ñ.Ô.Ð.Ñ.Ø×%Ò% jÑ1Ô1ñ ;rà#œz×;Ò;ØÐ!2Ñ2°D´NÀDÄJ×DTÒDTÑDVÔDVñ ô  �ð  Ð'Ø!%¤¨KÔ!8�JØ! TÔ%5Ð5Ð5Ø%)Ô%5°jÔ%A˜
Ø)×2Ò2°6Ñ:Ô:ÐcÐcÐ<cÈ*Ð<cÐ<cÐ<cÑcÔcÐ:Ø)œ×7Ò7¸ÑFÔFÐsÐsÐHsÐV`ÐHsÐHsÐHsÑsÔsÐFØ'1¤Ô'BÔ'L˜˜ð  *¨TÔ->Ð>Ð>Ð>ð,¸*ð ,ð ,ð ,ñ  ?Ô>Ð>ð
 (,Ô'8¸Ô'D˜Ø+/×+IÒ+IØ˜k¨4Ô+@È|ð ,Jñ ,ô ,Ð(ð ,Ð3Ø7Ð7Ð7Ø$ð ;Ø×*Ò*Ð+?Ñ@Ô@Ð@Ð@àŸšÐ%9Ñ:Ô:Ð:Ø#7¸Ô#;�LàÔ'Ð+;Ò;Ð;Ø)×0Ò0°Ô1DÑEÔEÐEØ×&Ò& |Ô'9¸!Ô'<Ñ=Ô=Ð=Ø$×+Ò+¨LÔ,>¸qÔ,AÑBÔBÐBÑBà)×0Ò0°Ô1DÀQÔ1GÑHÔHÐHØ×&Ò& |Ô':¸1Ô'=Ñ>Ô>Ð>Ø$×+Ò+¨LÔ,?ÀÔ,BÑCÔCÐCÑCØ”Ð(ð ”K×1Ò1ØØ �MØ1MØ!-Ø)=ØØ"&ð 2ñ ô ñØ0Ø+Ø&Øð &×,Ò,Ð-IÈ!Ô-LÑMÔMÐMØ×"Ò"Ð#5°aÔ#8Ñ9Ô9Ð9Ø ×'Ò'Ð(?ÀÔ(BÑCÔCÐCÑCõ !Ð!pÀZÐ!pÐ!pÐ^bÔ^nÐ!pÐ!pÑqÔqÐqà$Ð&6¸ÀUÐJÐJr'   c                 ó  — |j         | j        v r&| j        |j                  }|j        |j        |j        fS |                      ||||¦  «        \  }}}t          |j         |||t          j        d¦  «        }|| j        |j         <   |||fS )aš  
        :param weight: TensorProto initializer
        :param qType: type to quantize to
        :param keep_float_weight: Whether to quantize the weight. In some cases, we only want to qunatize scale and zero point.
                                  If keep_float_weight is False, quantize the weight, or don't quantize the weight.
        :return: quantized weight name, zero point name, scale name
        N)	r"   rT   rm  r=  r/  Úquantize_initializer_implr   r   r…  )	rW   r¾   rÐ   rY   Úkeep_float_weightr“  r«  r=  r/  s	            r%   r¥  z"ONNXQuantizer.quantize_initializerø  s®   € ð Œ;˜$Ô2Ð2Ð2Ø"Ô6°v´{ÔCˆOàÔ&ØÔ'ØÔ*ðð ð .2×-KÒ-KØ�E˜<Ð):ñ.
ô .
Ñ*ˆ�w 
õ
 )ØŒKØØØÝÔ*Øñ
ô 
ˆð 1@ˆÔ  ¤Ñ-Ø˜g zÐ1Ð1r'   c                 óê   — || j         v r!| j         |         }|j        |j        |j        fS |                      |||||¦  «        \  }}}	t          |||	|t          j        |¦  «        }|| j         |<   |||	fS r”   )rT   rm  r=  r/  Ú quantize_weight_per_channel_implr   r   r…  )
rW   rK  rZ   Úchannel_axisrY   r³  r“  r«  r=  r/  s
             r%   r¤  z)ONNXQuantizer.quantize_weight_per_channel  s¨   € ð ˜$Ô2Ð2Ð2Ø"Ô6°{ÔCˆOàÔ&ØÔ'ØÔ*ðð ð .2×-RÒ-RØ˜ |°\ÐCTñ.
ô .
Ñ*ˆ�w 
õ )ØØØØÝÔ*Øñ
ô 
ˆð 1@ˆÔ  Ñ-à˜g zÐ1Ð1r'   c                 ó‚  — || j         v �r4|| j        v�r*| j         |         }t          |j        | j                             ¦   «         ¦  «        }| j        j        j        dk    s| j        j        j        dk    r5|�3|j        €,|�*t          j	         
                    |¦  «        j        dk    sJ ‚|dz   }| j                             || j        | j                             ¦   «         ¦  «        }|€@|j        |j        |j        g}t          j                             d||g||j        ¬¦  «        }|S ||j        d         k    sJ ‚dS )a¶  
        Given a value (input/output) which is quantized, add a DequantizeLinear node to dequantize
        it back to float32 or float16
            parameter value_name: value to dequantize
            parameter new_nodes_list: List of new nodes created before processing current node
            return: None if there is already a DequantizeLinear node that dequantizes it
                    A DequantizeLinear node otherwise
        ra   Nr   Ú_DequantizeLinearr‰   )rq  r   )rT   rV   r   r/  r9   r�   rb   rq  rd   ro  rp  r\  r¦  rG   r;   rm  r=  re   r   r?   )rW   Ú
value_namer“  rx  Údqlinear_nameÚdqlinear_nodeÚdqlinear_inputsÚdequantize_nodes           r%   Ú_dequantize_valuezONNXQuantizer._dequantize_value9  sb  € ð ˜$Ô2Ð2Ñ2¸È4ÔKeÐ9eÑ9eØ"Ô6°zÔBˆOõ & oÔ&@À$Ä*×BXÒBXÑBZÔBZÑ[Ô[ˆJð ŒzÔÔ-Ð1AÒAÐAØ”
Ô Ô.Ð2BÒBÐBÀzÐG]ð #Ô'Ð/Ø%Ð-µÔ1B×1KÒ1KÈJÑ1WÔ1WÔ1\Ð`aÒ1aÐ1aÐ1aÐaà&Ð)<Ñ<ˆMØ œJ×8Ò8¸ÈÌÐX\ÔXb×XhÒXhÑXjÔXjÑkÔkˆMØÐ$à#Ô*Ø#Ô.Ø#Ô+ð#�õ
 #'¤+×"7Ò"7Ø&Ø#Ø�LØ!Ø(Ô-ð #8ñ #ô #�ð 'Ð&ð " ]Ô%9¸!Ô%<Ò<Ð<Ð<Ð<Øˆtr'   c                 ó´   — | j                              ¦   «         j        D ]8}|                      |j        ¦  «        }|�| j                             |¦  «         Œ9dS )zÃ
        Dequantize output if it is quantized
            parameter new_nodes_list: List of new nodes created before processing current node
            return: List of new nodes created
        N)r9   r;   r?   r¾  r"   rG   rã   )rW   r?   r½  s      r%   r¢   z!ONNXQuantizer._dequantize_outputse  s`   € ð ”j×&Ò&Ñ(Ô(Ô/ð 	7ð 	7ˆFØ"×4Ò4°V´[ÑAÔAˆOØÐ*Ø”×%Ò% oÑ6Ô6Ð6øð	7ð 	7r'   c           	      óÐ  — | j         €d S |                      ¦   «          i }| j         D �]½}| j         |         }t          |t          ¦  «        s#t	          dt          |¦  «        › d|›d�¦  «        ‚| j                             |i ¬¦  «        }| j        }d|v r|d         j	        }d|v rd|v r|d         |d         }}�n|t          j        j        k    rt          ||j        d         ¦  «        \  }}nÞ|                     d	|j        d
         ¦  «        }|                     d|j        d         ¦  «        }	|                     d| j        ¦  «        }
|                     dd¦  «        }t%          |||
¬¦  «        \  }}t'          ||	|||
| j        ¦  «        \  }}| j        r3|t          j        j        k    r|
st/          ||	||| j        ¬¦  «        \  }}t1          |||¬¦  «        ||<   �Œ¿|S )Nr  r  rÂ   )Údefault_valr  r  r  r   rg  r   rh  Ú	symmetricrY   F)rY   rÂ  )ÚqminÚqmaxÚmin_real_range)r  r  r  )r\   Úadjust_tensor_rangesr  r   r  rq   Útensor_quant_overridesÚget_per_tensor_overridesr[   r·   rd   rÅ   ÚFLOAT8E4M3FNr   Úavg_stdÚgetÚrange_valueÚis_activation_symmetricr   r   rÅ  Ú#is_activation_restricted_asymmetricrÌ   r   r   )rW   rO   r´   ÚtdÚquant_overridesr  Úzeror  rg  rh  rÂ  rY   rÃ  rÄ  s                 r%   rN   z+ONNXQuantizer.calculate_quantization_paramsq  s#  € ØÔÐ%Ø�4à×!Ò!Ñ#Ô#Ð#à ÐØÔ-ð 	wñ 	wˆKØÔ# KÔ0ˆBÝ˜b¥*Ñ-Ô-ð TÝÐ Rµ4¸±8´8Ð RÐ RÀ+Ð RÐ RÐ RÑSÔSÐSà"Ô9×RÒRÐS^ÐlnÐRÑoÔoˆOàÔ.ˆJØ˜Ð.Ð.Ø,¨\Ô:ÔF�
à˜/Ð)Ð)¨l¸oÐ.MÐ.MØ-¨lÔ;¸_ÈWÔ=U�e�‘Ø�tÔ/Ô<Ò<Ð<Ý5°jÀ"Ä*ÈQÄ-ÑPÔP‘��e�eà&×*Ò*¨6°2´>À!Ô3DÑEÔE�Ø&×*Ò*¨6°2´>À!Ô3DÑEÔE�Ø+×/Ò/°¸TÔ=YÑZÔZ�	Ø.×2Ò2°>À5ÑIÔI�Ý4°ZÈlÐfoÐpÑpÔp‘
��dÝ.¨t°T¸4ÀÀyÐRVÔReÑfÔf‘��eØÔ;ð À
ÍdÔN^ÔNdÒ@dÐ@dÐmvÐ@då":Ø˜d¨°DÈÔI\ð#ñ #ô #‘K�D˜%õ 0BÈTÐY^ÐkuÐ/vÑ/vÔ/vÐ Ñ,Ñ,à"Ð"r'   r”   )F)NN)NNN)r€  )FFr  F)TFFr  F)FF)TF)'Ú__name__Ú
__module__Ú__qualname__r8   rn   r…   rŽ   r‘   r—   ri   rµ   r¼   rÈ   rÒ   rË   rÍ   r3  r@  rB  rW  r  Úndarrayr¦   rd   rÅ   ÚboolÚtuplerj  r  r”  r–  rŸ  r¡  rž  r¥  r¤  r¾  r¢   rN   r    r'   r%   r   r   '   sã  € € € € € ð ðFMð FMð FMð FMðR/ð /ð /ð> fð  fð  fðD
ð 
ð 
ðð ð ð<ð <ð <ð+ ð + ð + ðZ
ð 
ð 
ð"ð ð ð ð2ð ð ð2Að Að AðRAð RAð RAðh\7ð \7ð \7ð|9Pð 9Pð 9Pð 9Pðx aeðD&ð D&ð D&ð D&ðLð ð ð" ð##ð ##ð ##ð ##ðJ6%à”Zð6%ð ”jð6%ð ð	6%ð
 Ô!ð6%ð ð6%ð 
ˆt�R”Z $Ñ&Ð&Ô	'ð6%ð 6%ð 6%ð 6%ðp$1¨cð $1¸b¼jð $1ÈTð $1ð $1ð $1ð $1ðLF#ð F#ð F#ð F#ðP
ð 
ð 
ð	
ð 	
ð 	
ð 	
ð" Ø"ØØð
ð 
ð 
ð 
ð. &*ØØ"ØØðAKð AKð AKð AKðF2ð 2ð 2ð 2ðL Øð2ð 2ð 2ð 2ð@*ð *ð *ðX
7ð 
7ð 
7ð%#ð %#ð %#ð %#ð %#r'   r   )$r�   Únumpyr  rd   Úonnx.numpy_helperr   rÄ   Úbase_quantizerr   r   Ú	calibrater   Ú
onnx_modelr   Úquant_utilsr	   r
   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   Úregistryr   r   r    r'   r%   ú<module>rß     s™  ðð €€€à Ð Ð Ð Ø €€€Ø Ð Ð Ð Ø &Ð &Ð &Ð &Ð &Ð &à =Ð =Ð =Ð =Ð =Ð =Ð =Ð =Ø !Ð !Ð !Ð !Ð !Ð !Ø !Ð !Ð !Ð !Ð !Ð !ðð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð( (Ð 'Ð 'Ð 'Ð 'Ð 'ðo#ð o#ð o#ð o#ð o#�Mñ o#ô o#ð o#ð o#ð o#r'   