
    *`i[                        d Z ddlZddl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l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mZ d	Zn# e$ r d
ZdZdZdZdZdZdZdZdZdZY nw xY wg dZ defdZ!	 dej"        j#        dej$        fdZ%dej"        j#        dej&        de'fdZ(	 dee)ej$        f         dej$        fdZ*dej"        j#        dej$        fdZ+	 d4dej"        j#        de'dej"        j,        deeej$        ed         f                  fdZ-	 d4dej"        j#        de'dej&        deeej$        ed         f                  fdZ.dej"        j#        de'fdZ/ e! ej0                              ej1        dej"        j#        fd                         Z2 e!d          	 d4d!eee
ef         d"e'd#ej&        deeej$        ed         f                  fd$            Z3 e!d          d!eee
ef         d"e'fd%            Z4 e! ej0                              ej1        dej"        j#        fd&                        Z5 e! ej0                              ej1        	 d4d'eej"        j#        eej"        j#                 f         d(eej$                 fd)                        Z6d*ej"        j#        de'dej"        j#        fd+Z7d*ej"        j#        de'fd,Z8 e!d-           ej$        d.          fdej"        j#        d(ej$        deej$        ed         f         dej"        j#        fd/            Z9dej"        j#        dej"        j#        fd0Z:ej1        d1             Z;	  e!d
          dej"        j#        de<fd2            Z= e! ej0                              ej1        	 d4dej"        j#        d(eej$                 fd3                        Z>dS )5aw  
Utilities associated with offloading functionality provided by `accelerate`.

| ------------------------------------------------------------------------------------------------------ | # noqa: E501
| Operation  | Without offloading support             | With offloading support                          | # noqa: E501
| ---------- | -------------------------------------- | ------------------------------------------------ | # noqa: E501
| Add        | module.register_parameter(name, param) | register_offload_parameter(module, name, param)  | # noqa: E501
| Check      | N/A                                    | has_offloaded_params(module)                     | # noqa: E501
| Onload     | N/A                                    | with align_module_device(module)                 | # noqa: E501
| Update     | module.name.data.copy_(new_data)       | update_offload_parameter(module, name, new_data) | # noqa: E501
| Delete     | del module.name                        | delete_offload_parameter(module, name)           | # noqa: E501
| Add Module | module.register_module(name, child)    | register_offload_module(name, child)             | # noqa: E501
| Del Module | del module.name                        | delete_offload_module(module, name)              | # noqa: E501
| ------------------------------------------------------------------------------------------------------ | # noqa: E501
    N)wraps)
attrgetter)AnyCallableDictIterableLiteralOptionalTupleUnion)
patch_attr)AlignDevicesHookadd_hook_to_moduleattach_align_device_hooknamed_module_tensorsremove_hook_from_module)OffloadedWeightsLoaderPrefixedDatasetfind_tied_parametersset_module_tensor_to_deviceTF)get_execution_deviceget_offloaded_deviceupdate_parameter_dataregister_offload_parameterupdate_offload_parameterdelete_offload_parameterhas_offloaded_paramsdisable_hf_hookdisable_offloadalign_modulesalign_module_deviceregister_offload_moduledelete_offload_moduleoffloaded_dispatchdisable_offloadingremove_dispatchcast_to_devicefallbackc                 H     dt           t          gt          f         f fd}|S )Nfuncc                     t           s;dk    rt          |           d             }nt          |           fd            }|S | S )Nerrorc                       t          d          )Nz9Please install `accelerate` in order to use this function)
ValueError)argskwargss     t/home/jaya/work/projects/VOICE-AGENT/VIET/agent-env/lib/python3.11/site-packages/compressed_tensors/utils/offload.pyfallback_fnz8check_accelerate.<locals>.decorator.<locals>.fallback_fn`   s    $S      c                      S N )r/   r0   r(   s     r1   r2   z8check_accelerate.<locals>.decorator.<locals>.fallback_fnh   s    #Or3   )_has_accelerater   )r*   r2   r(   s     r1   	decoratorz#check_accelerate.<locals>.decorator\   sr     	7""t    t$ $ $ $ $ r3   )r   r   )r(   r8   s   ` r1   check_accelerater9   [   s;    #,      ( r3   modulereturnc                     t          |           rOt          | j        j                                                  d         }| j        j        j        }||         j        S t          |           S )zk
    :param module: module to check
    :return: device module is offloaded to onto after forward pass
    r   )r   list_hf_hookweights_mapkeysdatasetdevicer   )r:   	first_keyprefix_datasets      r1   r   r   v   sb    
 F## ,499;;<<Q?	4<i(// $F+++r3   new_param_data
param_namec                 (    t          | ||           dS )aG  
    Update the data of an existing parameter and its offload dict. Supports both
    parameters of offloaded modules and non-offloaded modules

    :param module: module containing the parameter to update
    :param new_param_data: tensor to update parameter with
    :param param_name: name of module parameter to update
    N)r   )r:   rE   rF   s      r1   r   r      s     VZ@@@@@r3   device_specc                 n    t          | t                    rt          j        | dk    rd|  nd          S | S )a  
    Convert an integer device index or torch.device into a torch.device object.

    :param device_spec: Device index (int) or torch.device object.
                        Negative integers map to CPU.
    :return: torch.device corresponding to the given device specification.
    r   zcuda:cpu)
isinstanceinttorchrB   )rH   s    r1   r'   r'      sE     +s## R|[A5E5E1K1115QQQr3   c                 :   |                                  D ][}t          |          rt          |j        j                  c S t          |                    d          d          }|	|j        c S \t          j	        d|  d           t          j        d          S )z
    Get the device which inputs should be moved to before module execution.
    Assume that modules execute in the same order as returned by `model.modules()`

    :param module: module to check, may be offloaded
    :return: onload device of module
    FrecurseNz"Unable to get execution device of z, falling back to CPUrJ   )modulesr   r'   r>   execution_devicenext
parametersrB   warningswarnrM   )r:   	submoduleparams      r1   r   r      s     ^^%%    		** 	G!)"4"EFFFFFY))%)88$??<  MTvTTTUUU<r3   name	parameteroffload_devicediskc                    t          d |                                 D                       }|                     ||           t          |           r| j        }|j        J |j        |j        |<   t          |j        ||j	        |           |j        |         }|j
        i |j
        |                                <   |st          | |d           dS dS dS )aj  
    Register a parameter to the given module which may be offloaded

    :param module: maybe offloaded module
    :param name: name of newly registered parameter
    :param parameter: parameter being registered
    :param offload_device: device on which weight will be offloaded to. If None is
        provided, then infer device from parameters on module
    c              3   P   K   | ]!}|j         t          j         d           k    V  "dS )metaN)rB   rM   ).0ps     r1   	<genexpr>z-register_offload_parameter.<locals>.<genexpr>   s3      SS!QXf!5!55SSSSSSr3   Nr_   )anyrT   register_parameterr   r>   r?   rB   original_devicesoffload_to_weights_mapdatatied_params_mapdata_ptrr   )r:   rY   rZ   r[   
has_onloadhook	offloadeds          r1   r   r      s     SSv?P?P?R?RSSSSSJ
dI... F## >!'+++ '0&6d# 	t/y~~VVV $T*	+9;D !3!3!5!56  	>'f=====#> > 	> 	>r3   rg   c                    t          | |          }|j        j        |j        k    r)t          j        d|j        j         d|j                    |j        t          j        d          k    r#||j        ur|j                            |           t          |           r | j	        j
        }t          ||||           dS dS )a  
    Update the data of an existing parameter and its offload dict. Supports both
    parameters of offloaded modules and non-offloaded modules

    :param module: module containing the parameter to update
    :param name: name of module parameter to update
    :param data: tensor to update parameter with
    :param offload_device: device on which weight will be offloaded to. If None is
        provided, then infer device from parameters on module
    z!Shape of parameter being updated z% does not match shape of update data r_   N)getattrrg   shaperU   rV   rB   rM   copy_r   r>   r?   rf   )r:   rY   rg   r[   rX   r?   s         r1   r   r      s      !( 5 5Ez4:%%+
0@ + +"j+ +	
 	
 	
 |u|F++++EJ0F0F
 F## Ho1{D$GGGGGH Hr3   c                     t          | |           t          |           r| j        j        }t	          ||           dS dS )z
    Delete a parameter from a module which may be offloaded

    :param module: maybe offloaded module
    :param name: name of parameter being deleted
    N)delattrr   r>   r?   delete_from_weights_map)r:   rY   r?   s      r1   r   r      sN     FDF## 3o1T222223 3r3   )r(   c              #      K   i fd}|                      |           d V                                  D ]\  }}t          ||           d S )Nc                 ^    t          | d          r| j        | <   t          |            d S d S )Nr>   )hasattrr>   r   )r:   hookss    r1   collect_hooksz&disable_hf_hook.<locals>.collect_hooks  s>    6:&& 	,"OE&M#F+++++	, 	,r3   )applyitemsr   )r:   rx   rW   rk   rw   s       @r1   r   r     s|       E, , , , ,
 LL	EEE ;;== , ,	49d++++, ,r3   r?   keyvaluec                 \   t          | t                    rK|dk    rt          dt          |                      | j        }| j         | }t          ||||           dS t          | t                    ri|| j        vr| j        	                    |           t          | j                  dk    r|dk    rt          | j        |||           dS t          d          t          | t                    r|dk    rt          dt          |                      |Y|| v r| |         j        }nGt!          t#          |                                           d          }|t          d          |j        }|                    |          | |<   dS t          dt          |                      )	a  
    Helper function which implements offloaded item assignment for PrefixedDataset,
    OffloadedWeightsLoader, and Dict types.

    :param weights_map: weight map to be updated with offload information
    :param key: key used to identify weight location
    :param value: weight being offloaded
    :param offload_device: device on which weight will be offloaded to. If None is
        provided, then infer device from parameters in weights_map
    r\   z!Cannot offload to disk with type r   z@Updating weights_map with disk offloading is not implemented yetNz2Cannot infer offload device from empty weights_maprB   >Updating offload data not implemented for weights_map of type )rK   r   r.   typerA   prefixrf   r   all_keysappendlenindex
state_dictNotImplementedErrordictrB   rS   itervaluesto)r?   r{   r|   r[   rA   tenss         r1   rf   rf      s   " +// *
V##TkARARTTUUU%#*S**wUNCCCCC	K!7	8	8 "
k*** '',,,{ !!Q&&>V+C+C";#93~VVVVV &R   
K	&	& 
V##TkARARTTUUU !k!!!,S!1!8D!3!3!5!566==<$L   "& 88>8::C "#K  # #
 
 	
r3   c                    t          | t                    r$| j        }| j         | }t	          ||           d S t          | t
                    r>t          | j                  dk    rt	          | j        |           d S t          d          t          | t                    r| |= d S t          dt          |                      )Nr   zCDelete from weights_map with disk offloading is not implemented yetr   )rK   r   rA   r   rs   r   r   r   r   r   r   r   )r?   r{   rA   s      r1   rs   rs   ^  s    
 +// 
%#*S**-----	K!7	8	8 
{ !!Q&&#K$:C@@@@@ &U   
K	&	& 
 "#K  # #
 
 	
r3   c              #   l   K   t          |           rd| j        _        dV  d| j        _        dS dV  dS )z
    Context manager to disable module onloading and offloading. Parameters will stay on
    their current device

    :param module: module to disable offloading for
    FNT)r   r>   offloadr:   s    r1   r   r   {  sH       F## "'"&r3   rQ   rR   c              #   F  K   t          | t          j        j                  r| fn| } t	          j                    5 }| D ]G}|                    t          ||                     |                    t          |                     HdV  ddd           dS # 1 swxY w Y   dS )a2  
    Context manager for onloading modules to a device, and disabling onload and offload
    attempts triggered by forward calls. Used for sequential onloading of layers

    :param modules: `torch.nn.Module` or iterable of `torch.nn.Module`s to onload
    :param execution_device: device to onload to
    N)	rK   rM   nnModule
contextlib	ExitStackenter_contextr!   r   )rQ   rR   stackr:   s       r1   r    r      s       'w@@MwjjgG				 5 	9 	9F 3F<L M MNNN 7 78888	                 s   ABBBbasec           
         t          |           r<| j        }|j        sJ |j        J d}d}t	          |                                           j        }t          |           }t          |||          D ]p\  }}	|		                    |          }
|j
        i |j
        |
                                <   t          |j        | d| |
           |j        rt          |||           q|j        s`t          |j        j        |j        j         | d          }t%          |j        |j        d|||d|j
                  }t)          ||           |                     ||           dS )z
    Register a submodule with offloading if the parent module is offloaded

    :param base: module to attach submodule to
    :param name: name of submodule
    :param module: submodule to attach
    NFT)include_buffersrP   .)r   )rR   r   io_same_devicer?   offload_buffersplace_submodules	skip_keysrh   )r   r>   r   r?   rS   rT   rB   r   r   r   rh   ri   rf   r   r   r   rA   r   r   rR   r   register_module)r   rY   r:   rk   r   r   current_devicer[   rF   rX   rl   r?   submodule_hooks                r1   r"   r"     s    D!! +7!%||+++ ! doo//007-d33 "6O=M"
 "
 "
 
	P 
	PJ 00I#/=?$Y%7%7%9%9:"4#35K5Kz5K5KYWWW $ P+FJOOO $ 	7) (D4D4K1TT1T1T1T  K .!%!6$' /!1 $ 4	 	 	N v~666v&&&&&r3   c                     t          | |          }t          |                                          D ]\  }}t          ||           t	          | |           dS )z
    Delete a submodule from a model which may contain offloading
    :param base: parent module to delete submodule from
    :param name: name of submodule on parent
    N)rn   r=   named_parametersr   rr   )r   rY   r:   rF   _s        r1   r#   r#     sc     &dD11Ff557788 5 5
A 4444D$r3   r,   rJ   c                    dk    rt          d          t          |            |                                 }fd|                                D             }t	          |          }t          |           }i }|D ]6}|D ]1} t          |          |                                           }	i ||	<   27t          | |d||           t          | ddd	d
           | S )a  
    Unlike `dispatch_model`, this function forces a module (and its submodules) to
    offload all parameters and replace them with meta tensors, utiliizing the
    `AlignDevicesHook` to control onloading and offloading.

    :param module: module containing parameters to offload
    :param execution_device: device that modules will onload and execute on
    :param offload_device: device that module parameters will offload to
    :return: module with offloading device hooks
    r\   z*Disk offloading is not currently supportedc                 B    i | ]\  }}||                               S r6   )r   )r`   r{   valr[   s      r1   
<dictcomp>z&offloaded_dispatch.<locals>.<dictcomp>  s+    QQQ(#s#svvn--QQQr3   )r   rB   T)rR   r   r?   rh   hf_device_maprJ   zcuda:0)fake_offload	fake_exec)
r   r&   r   rz   r   r   r   ri   r   setattr)
r:   rR   r[   r   r?   tied_paramsrh   grouprF   ri   s
     `       r1   r$   r$     s)     !"NOOO F ""$$JQQQQj>N>N>P>PQQQJ(J~VVVK 'v..KO + + 	+ 	+J-z*--f55>>@@H(*OH%%	+
 )'   $ FOe(%S%STTTMr3   c                     t          | d           t          | d          rt          | d           |                     d           | S )z
    Remove any existing dispatches from module

    :param module: module which may be dispatched with hf hooks
    :return: module without dispatch
    TrO   r   rJ   )r   rv   rr   r   r   s    r1   r&   r&   $  sP     FD1111v'' )(((
IIeMr3   c               #     K   t           j        t                      dt           ffd} t          t           d|           5  dV  ddd           n# 1 swxY w Y                                   D ]W\  }\  }}||_        |                    d          D ]\  }}t          |||j                   |	                    |d           XdS )z
    Keep modules onloaded and disable offloading until this context exits.
    Affects modules which have been hooked with accelerate's `AlignDevicesHook`
    selfc                 P     | |g|R i |}|vr| | j         f|<   d| _         |S )NF)r   )r   r:   r/   r0   retonloaded_modulesoriginal_pre_forwards        r1   keep_onload_pre_forwardz3disable_offloading.<locals>.keep_onload_pre_forward=  sO    ""4A$AAA&AA)))(,dl';V$ DL
r3   pre_forwardNFrO   )
r   r   r   r   rz   r   r   r   rg   post_forward)r   r:   rk   r   rY   rX   r   r   s         @@r1   r%   r%   3  sG      ,7MQVV&6        
$m5L	M	M                
 $4#9#9#;#; ( (w!2252AA 	? 	?KD%$VT5:>>>>&$''''	( (s   AAAc                 n    t          | d          o%t          | j        t                    o| j        j        S )ad  
    Checks if a module has offloaded parameters by checking if the given module has a
    AlignDevicesHook attached with offloading enabled

    Args:
        module (`torch.nn.Module`): The module to check for an offload hook.

    Returns:
        bool: `True` if the module has an offload hook and offloading is enabled,
        `False` otherwise.
    r>   )rv   rK   r>   r   r   r   s    r1   r   r   U  s8     	
## 	$v(899	$O#r3   c              #     K   t          |           r|| j        j        }|| j        _        	 | j                            |            dV  | j                            | d           ||| j        _        dS dS # | j                            | d           ||| j        _        w xY w|d |                     d          D             }	 |D ]}t          | ||           dV  |                                D ]\  }}t          | ||           dS # |                                D ]\  }}t          | ||           w xY wdV  dS )a~  
    Context manager that moves a module's parameters to the specified execution device.

    Args:
        module (`torch.nn.Module`):
            Module with parameters to align.
        execution_device (`torch.device`, *optional*):
            If provided, overrides the module's execution device within the context.
            Otherwise, use hook execution device or pass
    Nc                 $    i | ]\  }}||j         S r6   r~   )r`   rY   rX   s      r1   r   z'align_module_device.<locals>.<dictcomp>  s-     
 
 
#.4D%,
 
 
r3   FrO   )r   r>   rR   r   r   r   r   rz   )r:   rR   original_devicedevicesrY   rB   s         r1   r!   r!   j  s      F## '$o>O/?FO,	CO''///EEEO((666+3B000 ,+ O((666+3B0BBBB		%
 
282I2IRW2I2X2X
 
 
	B L L+FD:JKKKKEEE ' B Bf+FD&AAAAB B B Bf+FD&AAAAB 	s   A8 8+B#	D -D=r5   )?__doc__r   rU   	functoolsr   operatorr   typingr   r   r   r   r	   r
   r   r   rM   compressed_tensors.utilsr   accelerate.hooksr   r   r   r   r   accelerate.utilsr   r   r   r   r7   ImportError__all__r9   r   r   rB   r   Tensorstrr   rL   r'   r   	Parameterr   r   r   nullcontextcontextmanagerr   rf   rs   r   r    r"   r#   r$   r&   r%   boolr   r!   r6   r3   r1   <module>r      sH                      Q Q Q Q Q Q Q Q Q Q Q Q Q Q Q Q Q Q Q Q  / / / / / /                          OO 
  
  
 O"!O"&#
   *s    0 $, ,U\ , , , ,AHOA-2\AGJA A A A #
c5<&7 8 
U\ 
 
 
 
 U\    0 FJ	%> %>HO%>
%> x!%> U5<#@AB	%> %> %> %>X FJ	H HHOH
H ,H U5<#@AB	H H H HB3UX_ 3C 3 3 3 3 1:133444,EHO , , ,  54,  4   
 FJ	:
 :
.DDE:
	:
 <:
 U5<#@AB	:
 :
 :
 ! :
z 4   
.DDE
	
 
 
 ! 
8 1:133444EHO     54 1:133444 04 58?HUX_$==>u|,    54(6'%(/ 6' 6'eho 6' 6' 6' 6'r s     7### <H5<;N;N7 7HO7l7 %,787 X_	7 7 7 $#7tEHO      ( ( (:  5!!! T    "!( 1:133444HL' 'HO'/7/E' ' '  54' ' 's   A A/.A/