o
    i-`                     @   s  d dl Z d dlZd dlmZ d dlZd dlZd dlmZ d dlm	Z	m
Z
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 d d	lmZmZmZ d
ejd< e eZdej iZ!dCddZ"dd Z#dd Z$ej%fddZ&dd Z'dd Z(dd Z)dd Z*	dDddZ+de,d e,d!e-d"e.d#e.d$e
d%e.d&e.fd'd(Z/d)e,d*e,d+e,fd,d-Z0d.d/ Z1	dDd0d1Z2d2d3 Z3dEd5d6Z4d7d8 Z5d9d: Z6d;d< Z7d=d> Z8d?d@ Z9dAdB Z:dS )F    N)Path)AffinitySetting)OptimizerInfo	Precisioncreate_onnxruntime_session)MODEL_CLASSES)QuantizeHelper)torch_onnx_export)
AutoConfigAutoFeatureExtractorAutoTokenizerLxmertConfigTransfoXLConfig)PRETRAINED_GPT2_MODELSGPT2ModelNoPastStateTFGPT2ModelNoPastState2ZTF_CPP_MIN_LOG_LEVELtriuc                 C   s   |d u sJ t | jdkr| d| dksJ td }|tjdtjd|}|d | dd | df }t| | t	| S )N   r      r   )   r   dtype)
lenshapesize
torch_functorchonesuint8whereboolZ
zeros_like)xZdiagonaloutZ
torch_triutemplatemask r&   `/home/kim/smarthome/.venv/lib/python3.10/site-packages/onnxruntime/transformers/onnx_exporter.py	triu_onnx#   s   & r(   c                   C   s
   t t_d S N)r(   r   r   r&   r&   r&   r'   replace_torch_functions-   s   
r*   c                   C   s   t d t_d S )Nr   )r   r   r   r&   r&   r&   r'   restore_torch_functions1   s   r+   c           
      C   s  |j dv rtj|d|j|jtj}d|i}|S tjjd| d ||f|d}d|i}d|v r=tj||g|d	}||d< d
|v rNtj	||g|d	}	|	|d
< |j
rU||d< t|trxtjdd|jtj|d< tjdd|jtj|d< t|trtj	|jgtjd	|d< |S )NZvitswin   pixel_valuesr   r   lowhighr   r   	input_idsattention_maskr   Ztoken_type_idsdecoder_input_idsvisual_feats
visual_posz@tf_transfo_xl_model/transformer/pos_emb/einsum/Einsum/inputs_1:0)
model_typenumpyrandomZrand
image_sizeZastypeZfloat32randintr   Zzerosis_encoder_decoder
isinstancer   Zrandnvisual_feat_dimvisual_pos_dimr   hidden_size)

vocab_size
batch_sizesequence_lengthinput_namesconfigZ	data_typer3   inputsr4   Zsegment_idsr&   r&   r'   create_onnxruntime_input5   s,   




rH   c                 C   s&   i }|D ]}|| v r| | ||< q|S r)   r&   )rG   rE   Zremaining_model_inputsZ
input_namer&   r&   r'   filter_inputsS   s   rI   c                 C   s$   t | ttfrdd | D gS | gS )Nc                 S   s   g | ]}t |qS r&   )flatten.0ir&   r&   r'   
<listcomp>\   s    zflatten.<locals>.<listcomp>)r>   listtuple)rG   r&   r&   r'   rJ   [   s   $rJ   c                 C   s0   | D ]}t |ttfs||nt|| q|S r)   )r>   rO   rP   appendupdate_flatten_list)rG   Zres_listrM   r&   r&   r'   rR   _   s    rR   c           
      C   s   | d j d }dd | D }dd tt|D }t|D ]%\}}ddi||< || j }t|D ]\}}	|	|krA|| |d	i q0q||fS )
Nr3   c                 S   s   i | ]}|d ddqS )rC   seq_len)r   r   r&   rL   keyr&   r&   r'   
<dictcomp>h   s    z&build_dynamic_axes.<locals>.<dictcomp>c                 S   s   g | ]
}d t |d  qS )Zoutput_r   )strrK   r&   r&   r'   rN   j   s    z&build_dynamic_axes.<locals>.<listcomp>r   rC   rT   )r   ranger   	enumerateupdate)
example_inputsZoutputs_flattenrD   dynamic_axesoutput_namesrM   Zoutput_namedimsjdimr&   r&   r'   build_dynamic_axese   s   
rb   c              	   C   sN  t | |dd}|d u rt|  d dS t|  d dd | D }|||}t|t|krEtdt| dt|  dS tt|D ]Q}	t	t
||	 ||	    }
|
d	krntd
|
 d|	  |rrdnd	}|rxdnd	}tj||	 ||	   ||dstd|	 d| d|   dS qKtd|   dS )NF)Zenable_all_optimizationz is an invalid ONNX modelz is a valid ONNX modelc                 S   s   i | ]	\}}||  qS r&   )r9   )rL   ktr&   r&   r'   rW      s    z'validate_onnx_model.<locals>.<dictcomp>z"Number of output tensors expected z, got g-C6?zMax absolute diff=z for output tensor g?g?)rtolatolzOutput tensor z is not close: rtol=z, atol=z0inference result of onnxruntime is validated on T)r   loggererrorinfoitemsrunr   rY   r9   ZamaxabscpuZallclose)onnx_model_pathr\   example_outputs_flattenuse_gpuZfp16r^   Ztest_sessionZexample_ort_inputsZexample_ort_outputsrM   Zabs_diffre   rf   r&   r&   r'   validate_onnx_modelt   s:   $	rq   onnx_dir
model_nameinput_countoptimized_by_scriptrp   	precisionoptimized_by_onnxruntimeuse_external_datac                 C   s   ddl m} |dd|}	|s|	 d| }
n|rdnd}|	 d| d| d| }
|r/|
d7 }
| }|rG|sGtj| |
}tj|sGt| tj||
 dS )	Nr   )subz[^a-zA-Z0-9_]_Zgpurm   _ortz.onnx)rery   ospathjoinexistsmakedirs)rr   rs   rt   ru   rp   rv   rw   rx   ry   Znormalized_model_namefilenameZdevice	directoryr&   r&   r'   get_onnx_file_path   s   

r   	file_pathsuffixreturnc                 C   s&   t | }t|j|j| |jS )a  
    Append a suffix at the filename (before the extension).
    Args:
        path: pathlib.Path The actual path object we would like to add a suffix
        suffix: The suffix to add
    Returns: path with suffix appended at the end of the filename and before extension
    )r   rX   parentjoinpathstemwith_suffixr   )r   r   r~   r&   r&   r'   add_filename_suffix   s   r   c                 C   sh   |st j|s*t|jjddd ddlm}m} || ||dd}||||< d S t	
d|  d S )NTparentsexist_okr   )get_fusion_statisticsoptimize_by_onnxruntimec   )rp   optimized_model_path	opt_level'Skip optimization since model existed: )r}   r~   r   r   r   mkdir	optimizerr   r   rg   ri   )rn   ort_model_pathrp   	overwritemodel_fusion_statisticsr   r   rz   r&   r&   r'   optimize_onnx_model_by_ort   s   r   c              
   C   s   |st j|stt|jjddd ddlm} ddlm	} |d u r&||}|
| |tjkr3d|_|tjkr;d|_|dkrCd}d}|| |||d||dd}|d	ksW|d
kr[|  | |	|< |tjkrl|jdd |||
 d S td|  d S )NTr   r   )FusionOptions)optimize_modelFr-   )Z	num_headsrA   r   optimization_optionsrp   Zonly_onnxruntimeZ
bert_kerasZbert_tf)Zkeep_io_typesr   )r}   r~   r   r   r   r   fusion_optionsr   r   r   use_raw_attention_maskr   FLOAT16Zenable_gelu_approximationINT8Zenable_embed_layer_normZuse_dynamic_axesZget_fused_operator_statisticsZconvert_float_to_float16Zsave_model_to_filerg   ri   )rn   r   r8   num_attention_headsrA   rp   rv   r   r   r   use_external_data_formatr   r   r   Z	opt_modelr&   r&   r'   optimize_onnx_model   s>   




r   c                 C   sz   |d ur|t v r
|S tddt  | tv rdS dd l}|d| d ur'dS |d| d ur1dS |d	| d ur;d
S dS )NzValid model class:  r   r   z-squad$ZAutoModelForQuestionAnsweringz-mprc$Z"AutoModelForSequenceClassificationZgpt2ZAutoModelWithLMHeadZ	AutoModel)r   	Exceptionr   r   r|   search)rs   custom_model_classr|   r&   r&   r'   modelclass_dispatcher  s   r   Fc                 C   sz   t | |}|dkr|rtj| ||dS tj| ||dS |r!d| }td|gd}td|  t||}|j| ||dS )Nr   )rF   	cache_dirZTFtransformers)fromlistzModel class name: )r   r   from_pretrainedr   
__import__rg   ri   getattr)rs   rF   r   r   is_tf_modelZmodel_class_nameZtransformers_modulemodel_classr&   r&   r'   load_pretrained_model/  s   

r   c                 C   s@   t j| |d}t|drd|_|| t| |||d}||fS )Nr   return_dictF)rF   r   r   )r
   r   hasattrr   modifyr   )rs   r   r   config_modifierrF   modelr&   r&   r'   load_pt_modelB  s   

r   c                 C   sH   t j| |d}|| t }|  t| |||dd}|  ||fS )Nr   T)rF   r   r   r   )r
   r   r   r   Zget_affinityr   Zset_affinity)rs   r   r   r   rF   Zaffinity_settingr   r&   r&   r'   load_tf_modelN  s   
r   c                 C   s    ddl m} || \}}||fS )Nr   )tf2pt_pipeline)Zconvert_tf_models_to_pytorchr   )rs   r   rF   r   r&   r&   r'   load_pt_model_from_tfc  s   r   c                 C   s2  d}|rt ||||d|}|jtjjkr|||jfS |jtjjks+|tjks+|tjkrut	|| t
|d||d|}t||||j|j|||	|
||| |}|rYt |||||tjk|}|tjkrutd|  t||| td|  |jtjjkr|rt|d}t||||
| |||dv r|jfS |jfS )NTFzQuantizing model: zFinished quantizing model: r{   r,   )rq   namer   ZNOOPTrB   ZBYSCRIPTr   r   r   r   r   r   r   rA   rg   ri   r   Zquantize_onnx_modelZBYORTr   r   Z
num_labels)rs   r   r8   rr   rE   rp   rv   Zoptimize_infovalidate_onnxr   r   rF   r   rn   r\   ro   r^   r   is_valid_onnx_modelr   r   r&   r&   r'   validate_and_optimize_onnxm  s   



	
	r   c                  C   s  t | |||\}}|  d }d }|dv r;tj| |d}tjjdd|j|j d tjd	|j|jd}||dd}nt
j| |d}|j}|jd	dd}t||}|di |}t|ttfshJ d
t| t|}t|g }t|| t|d|	|
d|}|stj|std|  t|jjddd d }d }|dv rdd |D dg}}nt||\}}t  t |t|! |t|" ||d||d	 t#  ntd|  t$| |||||	|
|||||||||d |\}}}||||fS )Nr,   r   r      r.   r0   pt)return_tensorsThis is a sample inputz%type of output is not list or tuple: FExporting ONNX model to Tr   c                 S   s   i | ]}|d diqS )r   r/   r&   rU   r&   r&   r'   rW     s    z-export_onnx_model_from_pt.<locals>.<dictcomp>Zlogits)	r   argsfrE   r^   r]   Zdo_constant_foldingopset_versionr   !Skip export since model existed: r&   )%r   rm   r   r   r9   r:   r<   r;   r   Zreshaper   model_max_lengthencode_plusrI   r>   rO   rP   typerJ   rR   r   r   r}   r~   r   rg   ri   r   r   r   rb   r*   r	   valueskeysr+   r   ) rs   r   r   r8   r   r   r   rr   rE   rp   rv   optimizer_infor   r   r   r   r   rF   r   r\   max_input_sizeZimage_processordata	tokenizerexample_outputsro   rn   r]   r^   Zonnx_model_filer   rB   r&   r&   r'   export_onnx_model_from_pt  s   
 



r   c           (      C   s  dd l }|jg d tj| |d}|jd u r|ddi |j}t| |||\}}|	t
| |jdd|dd	d
}t||}|jrP|jdd|dd	d
j|d< | dkrl|jdd|jg|d< |jdd|jg|d< z|jrsd|_W n	 ty}   Y nw ||dd}d }| dks| dkrdg}|d }ddlm} ||}t|| t
|d|	|
d|}|r|d d n|}|stj|sUtd|  |st|jj d	d	d dd l!}dd l"}|j#$|j#j% g }|& D ]\} }!d gt
|!j' }"|(|j)t*|"|!j+| d q|j,j-|t*||||d\}#}#|rT|.|d}$|$/tj0| W d    n	1 s2w   Y  tj1tj0|d}tj|rNt2| t3|| ntd|  |d }t4| |||||	|
|||||||||||\}%}&}'|%|&|'|fS )Nr   ZGPUr   	pad_tokenz[PAD]r   tf
max_lengthT)r   r   paddingZ
truncationr5   zunc-nlp/lxmert-base-uncasedr   r6   r7   F)Ztrainingzxlnet-base-casedzxlnet-large-casedZlast_hidden_state)nestr   r   )r   )Zinput_signatureZopsetZlarge_modelZoutput_pathrz__MODEL_PROTO.onnxr   Z_tf)5Z
tensorflowrF   Zset_visible_devicesr   r   r   Zadd_special_tokensr   r   Zresize_token_embeddingsr   r   rI   r=   r3   r:   normalr?   r@   Z	use_cacher   Ztensorflow.python.utilr   rJ   r   r}   r~   r   rg   ri   r   r   r   zipfiletf2onnxloggingZ	set_levelERRORrj   r   rQ   Z
TensorSpecrP   r   convertZ
from_kerasZipFile
extractalldirnamer   removerenamer   )(rs   r   r   r8   r   r   r   rr   rE   rp   rv   r   r   r   r   r   r   r   r   r   rF   r   r\   r   r^   r   ro   rn   Ztf_internal_model_pathr   r   specsr   valuer_   rz   zZoptimized_onnx_pathr   rB   r&   r&   r'   export_onnx_model_from_tf=  s   






r   )r   Nr)   )F);r   r}   pathlibr   r9   r   Zaffinity_helperr   Zbenchmark_helperr   r   r   Zhuggingface_modelsr   Zquantize_helperr   Ztorch_onnx_export_helperr	   r   r
   r   r   r   r   Z0onnxruntime.transformers.models.gpt2.gpt2_helperr   r   r   environ	getLogger__name__rg   r   r   r(   r*   r+   Zint64rH   rI   rJ   rR   rb   rq   rX   intr!   r   r   r   r   r   r   r   r   r   r   r   r   r&   r&   r&   r'   <module>   sl   





,
!
;

ao