509318396
Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­Â�Â­
<!DOCTYPE html>
<html>
3
ÉiD;  ã               @   sþ   d dl Z d dlZd dlZd dlZddlmZ ddlmZmZ ddl	m
Z
 d\ZZZd \ZZe
eƒZ	G dd„ dƒZG dd„ deƒZG dd„ deƒZG dd„ deƒZG dd„ deƒZG dd„ deƒZG dd„ deƒZG dd„ dƒZG dd„ dƒZG dd„ dƒZdS )!é    Né   )Úplatform)ÚErrorÚErrorWithTraceback)Úcreate_loggerÚaddÚremoveÚremove2ÚsharedÚ	exclusivec               @   sB   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S )ÚTimeoutTimerzâ
    A timer for timeout checks (can also deal with "never timeout").
    It can also compute and optionally execute a reasonable sleep time (e.g. to avoid
    polling too often or to support thread/process rescheduling).
    Nc             C   sX   |dk	r|dk rt dƒ‚|| _|dkrB|dkr4d}ntd|d ƒ}|| _d| _d| _dS )ag  
        Initialize a timer.

        :param timeout: time out interval [s] or None (never timeout, wait forever) [default]
        :param sleep: sleep interval [s] (>= 0: do sleep call, <0: don't call sleep)
                      or None (autocompute: use 10% of timeout [but not more than 60s],
                      or 1s for "never timeout" mode)
        Nr   ztimeout must be >= 0g      ð?g      N@g      $@)Ú
ValueErrorÚtimeout_intervalÚminÚsleep_intervalÚ
start_timeÚend_time)ÚselfÚtimeoutÚsleep© r   ú/usr/lib64/python3.6/locking.pyÚ__init__   s    	zTimeoutTimer.__init__c             C   s   d| j j| j| j| j| jf S )Nz)<%s: start=%r end=%r timeout=%r sleep=%r>)Ú	__class__Ú__name__r   r   r   r   )r   r   r   r   Ú__repr__+   s    zTimeoutTimer.__repr__c             C   s&   t j ƒ | _| jd k	r"| j| j | _| S )N)Útimer   r   r   )r   r   r   r   Ústart0   s    

zTimeoutTimer.startc             C   s   | j dkrtj| j ƒ d S )Nr   )r   r   r   )r   r   r   r   r   6   s    
zTimeoutTimer.sleepc             C   s   | j d k	otjƒ | j kS )N)r   r   )r   r   r   r   Ú	timed_out:   s    zTimeoutTimer.timed_outc             C   s   | j ƒ rdS | jƒ  dS d S )NTF)r   r   )r   r   r   r   Útimed_out_or_sleep=   s    zTimeoutTimer.timed_out_or_sleep)NN)
r   Ú
__module__Ú__qualname__Ú__doc__r   r   r   r   r   r   r   r   r   r   r      s   
r   c               @   s   e Zd ZdZdS )Ú	LockErrorzFailed to acquire the lock {}.N)r   r    r!   r"   r   r   r   r   r#   E   s   r#   c               @   s   e Zd ZdZdS )Ú
LockErrorTzFailed to acquire the lock {}.N)r   r    r!   r"   r   r   r   r   r$   I   s   r$   c               @   s   e Zd ZdZdS )ÚLockTimeoutz/Failed to create/acquire the lock {} (timeout).N)r   r    r!   r"   r   r   r   r   r%   M   s   r%   c               @   s   e Zd ZdZdS )Ú
LockFailedz*Failed to create/acquire the lock {} ({}).N)r   r    r!   r"   r   r   r   r   r&   Q   s   r&   c               @   s   e Zd ZdZdS )Ú	NotLockedz/Failed to release the lock {} (was not locked).N)r   r    r!   r"   r   r   r   r   r'   U   s   r'   c               @   s   e Zd ZdZdS )Ú	NotMyLockz=Failed to release the lock {} (was/is locked, but not by me).N)r   r    r!   r"   r   r   r   r   r(   Y   s   r(   c               @   sl   e Zd ZdZddd„Zdd„ Zdd	„ Zd
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 )ÚExclusiveLocka/  An exclusive Lock based on mkdir fs operation being atomic.

    If possible, try to use the contextmanager here like::

        with ExclusiveLock(...) as lock:
            ...

    This makes sure the lock is released again if the block is left, no
    matter how (e.g. if an exception occurred).
    NFc             C   sP   || _ || _tjj|ƒ| _|p$tjƒ | _tjj| jd| j ƒ| _	|| _
d| _d S )Nz%s.%d-%xF)r   r   ÚosÚpathÚabspathr   Úget_process_idÚidÚjoinÚunique_nameÚkill_stale_locksÚstale_warning_printed)r   r+   r   r   r.   r1   r   r   r   r   h   s    zExclusiveLock.__init__c             C   s   | j ƒ S )N)Úacquire)r   r   r   r   Ú	__enter__q   s    zExclusiveLock.__enter__c             G   s   | j ƒ  d S )N)Úrelease)r   Úexcr   r   r   Ú__exit__t   s    zExclusiveLock.__exit__c             C   s   d| j j| jf S )Nz<%s: %r>)r   r   r0   )r   r   r   r   r   w   s    zExclusiveLock.__repr__c             C   sÎ   |d kr| j }|d kr| j}t||ƒjƒ }xžytj| jƒ W nl tk
rv   | jƒ rX| S | j	ƒ  |j
ƒ rrt| jƒ‚Y q, tk
r¨ } zt| jt|ƒƒd ‚W Y d d }~X q,X t| jdƒ� W d Q R X | S q,W d S )NÚwb)r   r   r   r   r*   Úmkdirr+   ÚFileExistsErrorÚby_meÚkill_stale_lockr   r%   ÚOSErrorr&   ÚstrÚopenr0   )r   r   r   ÚtimerÚerrr   r   r   r3   z   s&    $
zExclusiveLock.acquirec             C   s@   | j ƒ st| jƒ‚| jƒ s$t| jƒ‚tj| jƒ tj| jƒ d S )N)	Ú	is_lockedr'   r+   r;   r(   r*   Úunlinkr0   Úrmdir)r   r   r   r   r5   �   s    

zExclusiveLock.releasec             C   s   t jj| jƒS )N)r*   r+   Úexists)r   r   r   r   rB   ˜   s    zExclusiveLock.is_lockedc             C   s   t jj| jƒS )N)r*   r+   rE   r0   )r   r   r   r   r;   ›   s    zExclusiveLock.by_mec       
   "   C   sŠ  yt j| jƒ}W n tk
r$   dS X �x|D � ]ü}y4|jddƒ\}}|jddƒ\}}t|ƒ}t|ƒ}W n$ tk
rŒ   tjd|| jƒ dS X t	j
|||ƒr dS | jsÂ| js¾tjd|ƒ d| _dS y&t jt jj| j|ƒƒ tjd|ƒ W q. tk
�r* }	 z$| j�stjd	|t|	ƒƒ d| _dS d }	~	X q.X q.W yt j| jƒ W nD tk
�r„ }	 z&|	jtjk�rfdS tjd
t|	ƒƒ dS d }	~	X nX dS )NFú-r   Ú.z9Found malformed lock %s in %s. Please check/fix manually.zOFound stale lock %s, but not deleting because BORG_HOSTNAME_IS_UNIQUE is False.TzKilled stale lock %s.z0Found stale lock %s, but cannot delete due to %szFailed to remove lock dir: %s)r*   Úlistdirr+   ÚFileNotFoundErrorÚrsplitÚintr   ÚloggerÚerrorr   Úprocess_aliver1   r2   ÚwarningrC   r/   r=   r>   rD   ÚerrnoZ	ENOTEMPTY)
r   ÚnamesÚnameZhost_pidZ
thread_strÚhostZpid_strÚpidÚthreadrA   r   r   r   r<   ž   sH    zExclusiveLock.kill_stale_lockc             C   sD   | j ƒ r@x*tj| jƒD ]}tjtjj| j|ƒƒ qW tj| jƒ d S )N)rB   r*   rH   r+   rC   r/   rD   )r   rR   r   r   r   Ú
break_lockÐ   s    zExclusiveLock.break_lockc          
   C   sf   | j |kst‚tjj| jd| ƒ}| jƒ rT| jƒ rTt|dƒ� W dQ R X tj| j	ƒ || | _ | _	dS )z0migrate the lock ownership from old_id to new_idz%s.%d-%xr8   N)
r.   ÚAssertionErrorr*   r+   r/   rB   r;   r?   rC   r0   )r   Úold_idÚnew_idZnew_unique_namer   r   r   Úmigrate_lockÖ   s    
zExclusiveLock.migrate_lock)NNNF)NN)r   r    r!   r"   r   r4   r7   r   r3   r5   rB   r;   r<   rV   rZ   r   r   r   r   r)   ]   s   

	
2r)   c               @   sR   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d„ ZdS )Ú
LockRosterzÎ
    A Lock Roster to track shared/exclusive lockers.

    Note: you usually should call the methods with an exclusive lock held,
    to avoid conflicting access by multiple threads/processes/machines.
    NFc             C   s   || _ |ptjƒ | _|| _d S )N)r+   r   r-   r.   r1   )r   r+   r.   r1   r   r   r   r   è   s    zLockRoster.__init__c       	      C   sÚ   y¸t | jƒ�}tj|ƒ}W d Q R X | jr¶xŒttfD ]€}y|| }W n tk
rX   w2Y nX tƒ }xD|D ]<\}}}t	j
|||ƒr�|j|||fƒ qftjd||||ƒ qfW t|ƒ||< q2W W n ttfk
rÔ   i }Y nX |S )Nz:Removed stale %s roster lock for host %s pid %d thread %d.)r?   r+   ÚjsonÚloadr1   ÚSHAREDÚ	EXCLUSIVEÚKeyErrorÚsetr   rN   r   rL   rO   ÚlistrI   r   )	r   ÚfÚdataÚkeyZentriesÚelementsrS   rT   rU   r   r   r   r]   í   s&    
zLockRoster.loadc          
   C   s(   t | jdƒ�}tj||ƒ W d Q R X d S )NÚw)r?   r+   r\   Údump)r   rd   rc   r   r   r   Úsave  s    zLockRoster.savec             C   s*   yt j| jƒ W n tk
r$   Y nX d S )N)r*   rC   r+   rI   )r   r   r   r   r   
  s    zLockRoster.removec             C   s"   | j ƒ }tdd„ |j|g ƒD ƒƒS )Nc             s   s   | ]}t |ƒV  qd S )N)Útuple)Ú.0Úer   r   r   ú	<genexpr>  s    z!LockRoster.get.<locals>.<genexpr>)r]   ra   Úget)r   re   Úrosterr   r   r   rn     s    zLockRoster.getc                s   t ‡ fdd„|D ƒƒS )Nc             3   s   | ]}ˆ j |ƒ V  qd S )N)rn   )rk   re   )r   r   r   rm     s    z#LockRoster.empty.<locals>.<genexpr>)Úall)r   Úkeysr   )r   r   Úempty  s    zLockRoster.emptyc             C   s°   | j ƒ }ytdd„ || D ƒƒ}W n tk
r<   tƒ }Y nX |tkrT|j| jƒ n8|tkrj|j| jƒ n"|tkr€|j	| jƒ nt
d| ƒ‚tdd„ |D ƒƒ||< | j|ƒ d S )Nc             s   s   | ]}t |ƒV  qd S )N)rj   )rk   rl   r   r   r   rm     s    z$LockRoster.modify.<locals>.<genexpr>zUnknown LockRoster op %rc             s   s   | ]}t |ƒV  qd S )N)rb   )rk   rl   r   r   r   rm   (  s    )r]   ra   r`   ÚADDr   r.   ÚREMOVEÚdiscardÚREMOVE2r   r   rb   ri   )r   re   Úopro   rf   r   r   r   Úmodify  s    zLockRoster.modifyc             C   sl   | j |kst‚| jd }| _zBy| j|tƒ W n tk
rH   || _ Y nX || _ | j|tƒ W d|| _X dS )z0migrate the lock ownership from old_id to new_idFN)r.   rW   r1   rx   rv   r`   rs   )r   re   rX   rY   Zkillingr   r   r   rZ   +  s    zLockRoster.migrate_lock)NF)r   r    r!   r"   r   r]   ri   r   rn   rr   rx   rZ   r   r   r   r   r[   á   s   
r[   c               @   st   e Zd ZdZddd„Zdd„ Zdd	„ Zd
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d„ ZdS )ÚLockaú  
    A Lock for a resource that can be accessed in a shared or exclusive way.
    Typically, write access to a resource needs an exclusive lock (1 writer,
    no one is allowed reading) and read access to a resource needs a shared
    lock (multiple readers are allowed).

    If possible, try to use the contextmanager here like::

        with Lock(...) as lock:
            ...

    This makes sure the lock is released again if the block is left, no
    matter how (e.g. if an exception occurred).
    FNc             C   sT   || _ || _|| _|| _|p"tjƒ | _t|d ||d�| _t	|d |||d�| _
d S )Nz.roster)r.   r1   z
.exclusive)r.   r   r1   )r+   Úis_exclusiver   r   r   r-   r.   r[   Ú_rosterr)   Ú_lock)r   r+   r   r   r   r.   r1   r   r   r   r   N  s    zLock.__init__c             C   s   | j ƒ S )N)r3   )r   r   r   r   r4   [  s    zLock.__enter__c             G   s   | j ƒ  d S )N)r5   )r   r6   r   r   r   r7   ^  s    zLock.__exit__c             C   s   d| j j| jf S )Nz<%s: %r>)r   r   r.   )r   r   r   r   r   a  s    zLock.__repr__c          
   C   s|   |d kr| j }|p| jpd}|r<| j||ƒ | jjttƒ n6| j�* |d k	rZ| jj|tƒ | jjt	tƒ W d Q R X || _ | S )Ngš™™™™™É?)
rz   r   Ú_wait_for_readers_finishingr{   rx   r_   rs   r|   rt   r^   )r   r   r   r   r   r   r   r3   d  s    zLock.acquirec          	   C   s¢   t | j|ƒjƒ }xŒ| jjƒ  yH|d k	r4| jj|tƒ t| jj	t
ƒƒdkrLd S |d k	rb| jj|tƒ W n   | jjƒ  ‚ Y nX | jjƒ  |jƒ rt| jƒ‚qW d S )Nr   )r   r   r   r|   r3   r{   rx   rt   Úlenrn   r^   rs   r5   r   r%   r+   )r   r   r   r@   r   r   r   r}   s  s     


z Lock._wait_for_readers_finishingc          
   C   st   | j r8| jjttƒ | jjttƒr,| jjƒ  | jj	ƒ  n8| j�, | jjttƒ | jjttƒrf| jjƒ  W d Q R X d S )N)
rz   r{   rx   r_   rt   rr   r^   r   r|   r5   )r   r   r   r   r5   ˆ  s    
zLock.releasec             C   s   | j s| jdtd� d S )NT)r   r   )rz   r3   r^   )r   r   r   r   Úupgrade”  s    zLock.upgradec             C   s   | j r| jdtd� d S )NF)r   r   )rz   r3   r_   )r   r   r   r   Ú	downgradeš  s    zLock.downgradec             C   s   | j o| jjƒ o| jjƒ S )N)rz   r|   rB   r;   )r   r   r   r   Úgot_exclusive_lockž  s    zLock.got_exclusive_lockc             C   s   | j jƒ  | jjƒ  d S )N)r{   r   r|   rV   )r   r   r   r   rV   ¡  s    
zLock.break_lockc             C   sn   | j |kst‚|| _ | jr:| jj||ƒ | jjt||ƒ n0| j�$ | jj||ƒ | jjt||ƒ W d Q R X d S )N)r.   rW   rz   r|   rZ   r{   r_   r^   )r   rX   rY   r   r   r   rZ   ¥  s    zLock.migrate_lock)FNNNF)NNN)r   r    r!   r"   r   r4   r7   r   r3   r}   r5   r   r€   r�   rV   rZ   r   r   r   r   ry   ?  s   

ry   )r   r   r	   )r
   r   )rP   r\   r*   r   Ú r   Zhelpersr   r   rL   r   rs   rt   rv   r^   r_   r   r   r#   r$   r%   r&   r'   r(   r)   r[   ry   r   r   r   r   Ú<module>   s(   
5 ^