
    bi                        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Zd Zd Zdeeej                   f   d	eee	j$                  f   fd
Z G d de      Z G d de      Zd	eee	j$                  f   dee   fdZy)    N)Mapping)OptionalUnion)	safe_openc                    d }t        | j                        dk(  r!| j                  t        j                        } d}| j                         j                         }t        j                  j                  || d      }|2|t        |j                        }|t        |j                        d||<   |j                  dk(  r|d    }t        j                  ||j                  d|j                        }|d d  |d d  |j                          |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_arrays           S/home/cdr/jupyterlab/.venv/lib/python3.12/site-packages/accelerate/utils/offload.pyoffload_weightr#      s    E
6<<,,U[[)JJL E'',,~+d/CDK=$E',tEKK7HIkzzQd;ekkEKKXJ!HJqML    c                    t        |d         }|dk(  rd}|d   }|dk(  rd}t        j                  | ||d      }t        |d         d	k(  r|d	   }t	        j
                  |      }|d   dk(  r|j                  t        j                        }|S )
Nr    )   r
   r   r   r)r
   r   r   r   )tupler   r   lenr   tensorr   r   )weight_fileweight_infor   r
   r   s        r"   load_offloaded_weightr.   .   s    +g&'E{ E
YY{%u3GF
;w A%\\&!F7z)U^^,Mr$   c                    | t        |       dk(  ry t        j                  j                  |d      }t        j                  j	                  |      r,t        |d      5 }t        j                  |      }d d d        ni }j                  |        t        |dd      5 }t        j                  ||d       d d d        y # 1 sw Y   JxY w# 1 sw Y   y xY w)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_indexs        r"   save_offload_indexr>   D   s    }E
anlC	ww~~()$w7 	)1 IIaLM	) 	) 	 #	8 .A		-1-. .	) 	). .s   C C C	Csave_dir
state_dictc                     t        j                  | d       i }|j                         D ]  \  }}t        ||| |      } t	        ||        y)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#   r>   )r?   r@   r   name	parameters        r"   offload_state_dictrG   U   sQ     KK4(E%++- Giy$FG uh'r$   c                   2    e Zd ZdZdedefdZd Zd Zd Z	y)	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                      || _         || _        y NrJ   rK   )selfrJ   rK   s      r"   __init__zPrefixedDataset.__init__q   s    r$   c                 <    | j                   | j                   |    S rM   rN   rO   keys     r"   __getitem__zPrefixedDataset.__getitem__u   s    ||t{{mC5122r$   c                     t        | j                  D cg c]   }|j                  | j                        s|" c}      S c c}w rM   )iterrJ   
startswithrK   rR   s     r"   __iter__zPrefixedDataset.__iter__x   s.    DLLPSCNN4;;4OSPQQPs
    A A c                 ,    t        | j                        S rM   )r*   rJ   rO   s    r"   __len__zPrefixedDataset.__len__{   s    4<<  r$   N)
__name__
__module____qualname____doc__r   r   rP   rT   rX   r[   r&   r$   r"   rI   rI   h   s*      3R!r$   rI   c                       e Zd ZdZ	 	 	 	 ddeeej                  f   dee	ee
j                  f      defdZdefdZd	 Zd
 Zy)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                    |||t        d      |i n|| _        || _        |I|Gt        t        j
                  j                  |d            5 }t        j                  |      }d d d        |i n|| _	        t        | j                  j                               | _        | j                  j                  | j                  D cg c]  }|| j                  vs| c}       || _        y # 1 sw Y   xY wc c}w )NzWNeed either a `state_dict`, a `save_folder` or an `index` containing offloaded weights.r0   )
ValueErrorr@   rb   r6   r   r   r   r7   r8   r   r   keysall_keysextenddevice)rO   r@   rb   r   rh   r<   rS   s          r"   rP   zOffloadedWeightsLoader.__init__   s     +"5%-vww * 2"
&=[4bggll;=> %!		!% =Re
T__1134TZZTc3dmm;ScTU% % Us   C,C8C8,C5rS   c                    || j                   v r| j                   |   S | j                  |   }|j                  d      | j                  dn| j                  }d }	 t	        |d   d|      5 }|j                  |j                  d|            }d d d        d|v r"|j                  t        t        |d               }|j                  t        j                  |      k7  r|j                  |      }|S t        j                  j                  | j                  | d      }t        ||      S # 1 sw Y   xY w# t        $ rK t	        |d   dd      5 }|j                  |j                  d|            }d d d        n# 1 sw Y   nxY wY w xY w)Nsafetensors_filer   pt)	frameworkrh   r   r
   r	   )r@   r   getrh   r   
get_tensor	TypeErrortogetattrr   r   r   r   rb   r.   )rO   rS   r-   rh   r+   r<   r,   s          r"   rT   z"OffloadedWeightsLoader.__getitem__   sr   $//!??3''jjo??-.:"kk1Ut{{FFO{+=>$W]^ Obc\\+//-*MNFO +%75+g2F#GH}}V 446*Mggll4#3#3uD\B$[+>>O O O{+=>$W\] Oab\\+//-*MNFO O OOsB   D6 ,"D*D6 *D3/D6 6F
"E;2	F
;F	 F
	F
c                 ,    t        | j                        S rM   )rV   rf   rZ   s    r"   rX   zOffloadedWeightsLoader.__iter__   s    DMM""r$   c                 ,    t        | j                        S rM   )r*   rf   rZ   s    r"   r[   zOffloadedWeightsLoader.__len__   s    4==!!r$   )NNNN)r\   r]   r^   r_   dictr   r   Tensorr   r   r   PathLiker   rP   rT   rX   r[   r&   r$   r"   ra   ra      sm     /39=ell*+ eC$456 	(?s ?4#"r$   ra   submodule_namesc                     i }|D ]N  }|j                  | j                         D ci c]!  \  }}||k(  s|j                  |dz         r||# c}}       P |S c c}}w )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.
    .)r9   rD   rW   )r@   rw   resultmodule_namerS   params         r"   extract_submodules_state_dictr}      ss     F& 	
 	 #-"2"2"4C+%c8I)J U
	
	
 Ms   &ArM   )r7   r   collections.abcr   typingr   r   r   r   r   safetensorsr   r#   r.   r>   r   rv   rt   ru   rG   rI   ra   r   r}   r&   r$   r"   <module>r      s     	 # "   !*,."(sBKK'7!8 (d3PUP\P\K\F] (&!g !.@"W @"Fd33D.E X\]`Xa r$   