o
    0i                     @   s   d dl Z d dlZd dlmZ d dlmZmZ d dlZd dl	Z	d dl
mZ dddZdd Zd	d
 Zdeeejf deee	jf fddZG dd deZG dd deZdeee	jf dee fddZdS )    N)Mapping)OptionalUnion)	safe_openc                 C   s   d }t | jdkr| tj} d}|   }tj	|| d}|d ur8|d u r.t |j}|t
|jd||< |jdkrA|d  }tj||jd|jd}|d d  |d d < |  |S )Nztorch.bfloat16bfloat16.dat)dtypeshaper   zw+)r   moder	   )strr   viewtorchint16cpunumpyospathjoinlistr	   ndimnpmemmapflush)weightweight_nameoffload_folderindexr   arraytensor_file
file_array r    Z/sda-disk/www/egybert/egybert_env/lib/python3.10/site-packages/accelerate/utils/offload.pyoffload_weight   s    

r"   c                 C   s|   t |d }|dkrd}|d }|dkrd}tj| ||dd}t|d d	kr+|d	 }t|}|d dkr<|tj}|S )
Nr	   r    )   r   r   r   r)r   r	   r
   r   )tupler   r   lenr   tensorr   r   )weight_fileweight_infor	   r   r   r    r    r!   load_offloaded_weight.   s   
r*   c                 C   s   | d u s
t | dkrd S tj|d}tj|r5t|dd}t|}W d    n1 s/w   Y  ni }||  t|ddd}tj	||dd W d    d S 1 sWw   Y  d S )Nr   
index.jsonzutf-8)encodingw   )indent)
r&   r   r   r   isfileopenjsonloadupdatedump)r   r   offload_index_filefcurrent_indexr    r    r!   save_offload_indexD   s   
"r9   save_dir
state_dictc                 C   sB   t j| dd i }| D ]\}}t||| |d}qt||  dS )a  
    Offload a state dict in a given folder.

    Args:
        save_dir (`str` or `os.PathLike`):
            The directory in which to offload the state dict.
        state_dict (`Dict[str, torch.Tensor]`):
            The dictionary of tensors to offload.
    T)exist_ok)r   N)r   makedirsitemsr"   r9   )r:   r;   r   name	parameterr    r    r!   offload_state_dictU   s
   
rA   c                   @   s:   e Zd ZdZdedefddZdd Zdd	 Zd
d Z	dS )PrefixedDatasetz
    Will access keys in a given dataset by adding a prefix.

    Args:
        dataset (`Mapping`): Any map with string keys.
        prefix (`str`): A prefix to add when trying to access any element in the underlying dataset.
    datasetprefixc                 C   s   || _ || _d S NrC   rD   )selfrC   rD   r    r    r!   __init__q   s   
zPrefixedDataset.__init__c                 C   s   | j | j |  S rE   rF   )rG   keyr    r    r!   __getitem__u   s   zPrefixedDataset.__getitem__c                    s   t  fdd jD S )Nc                    s   g | ]
}|  jr|qS r    )
startswithrD   .0rI   rG   r    r!   
<listcomp>y   s    z,PrefixedDataset.__iter__.<locals>.<listcomp>)iterrC   rN   r    rN   r!   __iter__x   s   zPrefixedDataset.__iter__c                 C   
   t | jS rE   )r&   rC   rN   r    r    r!   __len__{      
zPrefixedDataset.__len__N)
__name__
__module____qualname____doc__r   r   rH   rJ   rQ   rS   r    r    r    r!   rB   h   s    rB   c                   @   sn   e Zd ZdZ				ddeeeejf  dee	ee
jf  dee fddZdefd	d
Zdd Zdd ZdS )OffloadedWeightsLoaderaC  
    A collection that loads weights stored in a given state dict or memory-mapped on disk.

    Args:
        state_dict (`Dict[str, torch.Tensor]`, *optional*):
            A dictionary parameter name to tensor.
        save_folder (`str` or `os.PathLike`, *optional*):
            The directory in which the weights are stored (by `offload_state_dict` for instance).
        index (`Dict`, *optional*):
            A dictionary from weight name to their information (`dtype`/ `shape` or safetensors filename). Will default
            to the index saved in `save_folder`.
    Nr;   save_folderr   c                    s   |d u r|d u r|d u rt d|d u ri n| _| _|d u rB|d urBttj|d}t|}W d    n1 s=w   Y  |d u rHi n| _	t
 j  _ j fdd j	D  | _d S )NzWNeed either a `state_dict`, a `save_folder` or an `index` containing offloaded weights.r+   c                    s   g | ]	}| j vr|qS r    )all_keysrL   rN   r    r!   rO      s    z3OffloadedWeightsLoader.__init__.<locals>.<listcomp>)
ValueErrorr;   rZ   r1   r   r   r   r2   r3   r   r   keysr[   extenddevice)rG   r;   rZ   r   r_   r7   r    rN   r!   rH      s   
zOffloadedWeightsLoader.__init__rI   c                 C   s>  || j v r
| j | S | j| }|dd ur| jd u rdn| j}d }z$t|d d|d}||d|}W d    n1 s@w   Y  W n+ tyq   t|d ddd}||d|}W d    n1 sjw   Y  Y nw d|v r|tt	|d }|jt	|kr||}|S t
j| j| d}t||S )Nsafetensors_filer   pt)	frameworkr_   r   r   r   )r;   r   getr_   r   
get_tensor	TypeErrortogetattrr   r   r   r   rZ   r*   )rG   rI   r)   r_   r'   r7   r(   r    r    r!   rJ      s0   




z"OffloadedWeightsLoader.__getitem__c                 C   rR   rE   )rP   r[   rN   r    r    r!   rQ      rT   zOffloadedWeightsLoader.__iter__c                 C   rR   rE   )r&   r[   rN   r    r    r!   rS      rT   zOffloadedWeightsLoader.__len__)NNNN)rU   rV   rW   rX   r   dictr   r   Tensorr   r   PathLiker   rH   rJ   rQ   rS   r    r    r    r!   rY      s     
rY   submodule_namesc                    s.   i }|D ] |  fdd|  D  q|S )a  
    Extract the sub state-dict corresponding to a list of given submodules.

    Args:
        state_dict (`Dict[str, torch.Tensor]`): The state dict to extract from.
        submodule_names (`List[str]`): The list of submodule names we want to extract.
    c                    s,   i | ]\}}| ks|  d  r||qS ).)rK   )rM   rI   parammodule_namer    r!   
<dictcomp>   s
    z1extract_submodules_state_dict.<locals>.<dictcomp>)r4   r>   )r;   rk   resultr    rn   r!   extract_submodules_state_dict   s   
rr   rE   )r2   r   collections.abcr   typingr   r   r   r   r   safetensorsr   r"   r*   r9   r   rj   rh   ri   rA   rB   rY   r   rr   r    r    r    r!   <module>   s   
&$C