B
    .l\1  ã               @   s€   d dl Z d dlZd dlZd dlZdZe d¡jZe d¡jZe d¡j	Z
e d¡j	Zdd„ Zdd„ ZG d	d
„ d
eƒZdd„ ZdS )é    Ni   ó   ió   dc             C   s   t |ƒ| ||d …< d S )Né   )Ú_pack_double_func)ÚdataÚposÚvalue© r	   ú:lib/python3.7/site-packages/prometheus_client/mmap_dict.pyÚ_pack_double   s    r   c             C   s   t |ƒ| ||d …< d S )Né   )Ú_pack_integer_func)r   r   r   r	   r	   r
   Ú_pack_integer   s    r   c               @   sJ   e Zd ZdZddd„Zdd„ Zdd„ Zd	d
„ Zdd„ Zdd„ Z	dd„ Z
dS )Ú
MmapedDicta…  A dict of doubles, backed by an mmapped file.

    The file starts with a 4 byte int, indicating how much of it is used.
    Then 4 bytes of padding.
    There's then a number of entries, consisting of a 4 byte int which is the
    size of the next field, a utf-8 encoded string key, padding to a 8 byte
    alignment, and then a 8 byte float which is the value.

    Not thread safe.
    Fc             C   sÚ   t ||rdndƒ| _|| _t | j ¡ ¡jdkr<| j t¡ t | j ¡ ¡j| _	t
j
| j ¡ | j	|rjt
jnt
jd| _i | _t| jdƒd | _| jdkr°d| _t| jd| jƒ n&|sÖx |  ¡ D ]\}}}|| j|< q¾W d S )NÚrbza+br   )Úaccessr   )ÚopenÚ_fÚ_fnameÚosÚfstatÚfilenoÚst_sizeÚtruncateÚ_INITIAL_MMAP_SIZEÚ	_capacityÚmmapZACCESS_READZACCESS_WRITEÚ_mÚ
_positionsÚ_unpack_integerÚ_usedr   Ú_read_all_values)ÚselfÚfilenameZ	read_modeÚkeyÚ_r   r	   r	   r
   Ú__init__&   s    &
zMmapedDict.__init__c             C   sä   |  d¡}|ddt|ƒd d    }t d t|ƒ¡  ¡ t|ƒ|d¡}xJ| jt|ƒ | jkr’|  jd9  _| j | j¡ t	 	| j 
¡ | j¡| _qJW || j| j| jt|ƒ …< |  jt|ƒ7  _t| jd| jƒ | jd | j|< d	S )
z0Initialize a value. Lock must be held by caller.zutf-8ó    r   r   zi{0}sdg        é   r   N)ÚencodeÚlenÚstructÚpackÚformatr    r   r   r   r   r   r   r   r   )r"   r$   ÚencodedZpaddedr   r	   r	   r
   Ú_init_value8   s    
"zMmapedDict._init_valuec       
      c   s¸   d}| j }| j}tj}xœ||k r²t||ƒd }|| |krLd}t|| j ƒ‚|d7 }|d|  ¡ ||ƒd }|d|d d   }||7 }t||ƒd }	| 	d¡|	|fV  |d7 }qW dS )z1Yield (key, value, pos). No locking is performed.r   r   z0Read beyond file size detected, %s is corrupted.r   z%sszutf-8N)
r    r   r+   Úunpack_fromr   ÚRuntimeErrorr   r)   Ú_unpack_doubleÚdecode)
r"   r   Zusedr   r0   Zencoded_lenÚmsgr.   Z
padded_lenr   r	   r	   r
   r!   I   s     
zMmapedDict._read_all_valuesc             c   s&   x |   ¡ D ]\}}}||fV  q
W dS )z1Yield (key, value, pos). No locking is performed.N)r!   )r"   ÚkÚvr%   r	   r	   r
   Úread_all_valuesb   s    zMmapedDict.read_all_valuesc             C   s.   || j kr|  |¡ | j | }t| j|ƒd S )Nr   )r   r/   r2   r   )r"   r$   r   r	   r	   r
   Ú
read_valueg   s    


zMmapedDict.read_valuec             C   s0   || j kr|  |¡ | j | }t| j||ƒ d S )N)r   r/   r   r   )r"   r$   r   r   r	   r	   r
   Úwrite_valuen   s    


zMmapedDict.write_valuec             C   s*   | j r&| j ¡  d | _| j  ¡  d | _ d S )N)r   r   Úclose)r"   r	   r	   r
   r:   u   s
    

zMmapedDict.closeN)F)Ú__name__Ú
__module__Ú__qualname__Ú__doc__r&   r/   r!   r7   r8   r9   r:   r	   r	   r	   r
   r      s   

r   c             C   s"   t t||ƒƒ}tj| ||gddS )z&Format a key for use in the mmap file.T)Z	sort_keys)ÚdictÚzipÚjsonÚdumps)Zmetric_nameÚnameZ
labelnamesZlabelvaluesÚlabelsr	   r	   r
   Úmmap_key}   s    rE   )rA   r   r   r+   r   ZStructr,   r   r   r0   r   r2   r   r   Úobjectr   rE   r	   r	   r	   r
   Ú<module>   s   c