
                         (   S r SSKrSSKJrJr  SSKJrJrJr  SSK	J
r
Jr  SrSrSr\" S	5      rS
rS rS r " S S\5      r " S S\5      r " S S\5      r " S S\5      r " S S\5      r " S S\5      rS rS rS rS!S jrS rS r S r!S  r"g)"zRef handling.

    N)PackedRefsExceptionRefFormatError)git_linevalid_hexshaZERO_SHA)GitFileensure_dir_existss   ref: s   refs/heads/s
   refs/tags/s    ~^:?*[s   ^{}c                     U R                  [        5      (       a!  U [        [        5      S R                  S5      $ [	        U 5      e)zPParse a symref value.

Args:
  contents: Contents to parse
Returns: Destination
N   
)
startswithSYMREFlenrstrip
ValueError)contentss    lib/third_party/dulwich/refs.pyparse_symref_valuer   1   s<     6""F&--g66
X
    c                     SU ;   d  U R                  S5      (       a  gSU ;  a  gSU ;   a  g[        U 5       H%  u  p[        XUS-    5      S:  d  U[        ;   d  M%    g   U S   S;   a  gU R	                  S	5      (       a  gS
U ;   a  gSU ;   a  gg)a  Check if a refname is correctly formatted.

Implements all the same rules as git-check-ref-format[1].

[1]
http://www.kernel.org/pub/software/scm/git/docs/git-check-ref-format.html

Args:
  refname: The refname to check
Returns: True if refname is valid, False otherwise
s   /.   .F   /s   ..       s   .locks   @{   \T)r   	enumerateordBAD_REF_CHARSendswith)refnameics      r   check_ref_formatr#   =   s     7--d337'"w1q5!"T)Q--? # r{e!!r   c                       \ rS rSrSrSS jr    SS jr    SS jrS rS r	     S S	 jr
S
 rS rSS jrS rSS jrS rS rS rS rS rS rS r    SS jrS rS r    SS jrS rS rS rSrg)!RefsContainer_   zA container for refs.Nc                     Xl         g N_logger)selfloggers     r   __init__RefsContainer.__init__b   s    r   c           	      P    U R                   c  g Uc  g U R                  XX4XVU5        g r(   r)   )r+   refold_shanew_sha	committer	timestamptimezonemessages           r   _logRefsContainer._loge   s+     <<?S7yGTr   c                 ,    [        U R                  5      e)zMake a ref point at another ref.

Args:
  name: Name of the ref to set
  other: Name of the ref to point at
  message: Optional message
)NotImplementedErrorset_symbolic_ref)r+   nameotherr3   r4   r5   r6   s          r   r;   RefsContainer.set_symbolic_refu   s      "$"7"788r   c                 ,    [        U R                  5      e)Get contents of the packed-refs file.

Returns: Dictionary mapping ref names to SHA1s

Note: Will return an empty dictionary when no packed-refs file is
    present.
)r:   get_packed_refsr+   s    r   rA   RefsContainer.get_packed_refs   s     "$"6"677r   c                     ga5  Return the cached peeled value of a ref, if available.

Args:
  name: Name of the ref to peel
Returns: The peeled value of the ref. If the ref is known not point to
    a tag, this will be the SHA the ref refers to. If the ref may point
    to a tag, but no cached information is available, None is returned.
N r+   r<   s     r   
get_peeledRefsContainer.get_peeled   s     r   c                    U(       a  [        U R                  U5      5      nO
[        5       nUR                  5        HV  u  pU
c  UR                  U	5        O!U R	                  SR                  X45      S XS9  U(       d  MD   UR                  U	5        MX     U H$  nU R                  SR                  X45      S US9  M&     g ! [         a     M  f = f)Nr   )r6   )	setsubkeysitemsaddset_if_equalsjoinremoveKeyErrorremove_if_equals)r+   baser=   r3   r4   r5   r6   prune	to_deleter<   valuer0   s               r   import_refsRefsContainer.import_refs   s     DLL./II ;;=KD}d#""IItl+T5 #  y$$T* ) C!!$))TK"8$!P    s   C
CCc                 ,    [        U R                  5      e)z#All refs present in this container.)r:   allkeysrB   s    r   r[   RefsContainer.allkeys   s    !$,,//r   c                 4    [        U R                  5       5      $ r(   )iterr[   rB   s    r   __iter__RefsContainer.__iter__   s    DLLN##r   c                 J    Ub  U R                  U5      $ U R                  5       $ )zRefs present in this container.

Args:
  base: An optional base to return refs under.
Returns: An unsorted set of valid refs in this container, including
    packed refs.
)rL   r[   )r+   rT   s     r   keysRefsContainer.keys   s%     <<%%<<>!r   c                     [        5       n[        U5      S-   nU R                  5        H.  nUR                  U5      (       d  M  UR	                  XCS 5        M0     U$ )zRefs present in this container under a base.

Args:
  base: The base to return refs under.
Returns: A set of valid refs in this container under the base; the base
    prefix is stripped from the ref names returned.
r   N)rK   r   r[   r   rN   )r+   rT   rb   base_lenr    s        r   rL   RefsContainer.subkeys   sQ     ut9q=||~G!!$''+, & r   c                     0 nU R                  U5      nUc  SnOUR                  S5      nU H  n XS-   U-   R                  S5         X$'   M!     U$ ! [         a     M2  f = f)z6Return the contents of this container as a dictionary.r   r   )rb   r   striprR   )r+   rT   retrb   keys        r   as_dictRefsContainer.as_dict   st    yy<D;;t$DCs!2 9 9$ ?@  
  s   A
A A c                 z    US;   a  gUR                  S5      (       a  [        USS 5      (       d  [        U5      eg)a  Ensure a refname is valid and lives in refs or is HEAD.

HEAD is not a valid refname according to git-check-ref-format, but this
class needs to be able to touch HEAD. Also, check_ref_format expects
refnames without the leading 'refs/', but this class requires that
so it cannot touch anything outside the refs dir (or HEAD).

Args:
  name: The name of the reference.
Raises:
  KeyError: if a refname is not HEAD or is otherwise not valid.
)   HEADs
   refs/stashNs   refs/   )r   r#   r   rG   s     r   _check_refnameRefsContainer._check_refname   sA     ++x((0@ab0J0J && 1Kr   c                 v    U R                  U5      nU(       d   U R                  5       R                  US5      nU$ )zRead a reference without following any references.

Args:
  refname: The name of the reference
Returns: The contents of the ref file, or None if it does
    not exist.
N)read_loose_refrA   get)r+   r    r   s      r   read_refRefsContainer.read_ref   s7     &&w/++-11'4@Hr   c                 ,    [        U R                  5      e)zRead a loose reference and return its contents.

Args:
  name: the refname to read
Returns: The contents of the ref file, or None if it does
    not exist.
)r:   rs   rG   s     r   rs   RefsContainer.read_loose_ref  s     "$"5"566r   c                 8   [         U-   nSn/ nUR                  [         5      (       aq  U[        [         5      S nUR                  U5        U R	                  U5      nU(       d   XB4$ US-  nUS:  a  [        U5      eUR                  [         5      (       a  Mq  XB4$ )z|Follow a reference name.

Returns: a tuple of (refnames, sha), wheres refnames are the names of
    references in the chain
r   Nr   ro   )r   r   r   appendru   rR   )r+   r<   r   depthrefnamesr    s         r   followRefsContainer.follow  s     D=!!&))s6{}-GOOG$}}W-H !! QJEqytn$ !!&)) !!r   c                     SS K nUR                  S[        5        U R                  U5      u  p4U(       d  S U4$ US   U4$ )Nr   zFRefsContainer._follow is deprecated. Use RefsContainer.follow instead.r   )warningswarnDeprecationWarningr}   )r+   r<   r   r|   r   s        r   _followRefsContainer._follow)  sG    W	
 "[[.(##h''r   c                 2    U R                  U5      (       a  gg)NTF)ru   )r+   r    s     r   __contains__RefsContainer.__contains__5  s    ==!!r   c                 H    U R                  U5      u  p#Uc  [        U5      eU$ )zQGet the SHA1 for a reference name.

This method follows all symbolic references.
)r}   rR   )r+   r<   _shas       r   __getitem__RefsContainer.__getitem__:  s(    
 T";4. 
r   c                 ,    [        U R                  5      e)a  Set a refname to new_ref only if it currently equals old_ref.

This method follows all symbolic references if applicable for the
subclass, and can be used to perform an atomic compare-and-swap
operation.

Args:
  name: The refname to set.
  old_ref: The old sha the refname must refer to, or None to set
    unconditionally.
  new_ref: The new sha the refname will refer to.
  message: Message for reflog
Returns: True if the set was successful, False otherwise.
)r:   rO   )r+   r<   old_refnew_refr3   r4   r5   r6   s           r   rO   RefsContainer.set_if_equalsD  s    0 "$"4"455r   c                 ,    [        U R                  5      e)z~Add a new reference only if it does not already exist.

Args:
  name: Ref name
  ref: Ref value
  message: Message for reflog
)r:   
add_if_newr+   r<   r0   s      r   r   RefsContainer.add_if_new^  s     "$//22r   c                 *    U R                  USU5        g)as  Set a reference name to point to the given SHA1.

This method follows all symbolic references if applicable for the
subclass.

Note: This method unconditionally overwrites the contents of a
    reference. To update atomically only if the reference has not
    changed, use set_if_equals().

Args:
  name: The refname to set.
  ref: The new sha the refname will refer to.
N)rO   r   s      r   __setitem__RefsContainer.__setitem__h  s     	4s+r   c                 ,    [        U R                  5      e)a  Remove a refname only if it currently equals old_ref.

This method does not follow symbolic references, even if applicable for
the subclass. It can be used to perform an atomic compare-and-delete
operation.

Args:
  name: The refname to delete.
  old_ref: The old sha the refname must refer to, or None to
    delete unconditionally.
  message: Message for reflog
Returns: True if the delete was successful, False otherwise.
)r:   rS   )r+   r<   r   r3   r4   r5   r6   s          r   rS   RefsContainer.remove_if_equalsx  s    , "$"7"788r   c                 (    U R                  US5        g)a3  Remove a refname.

This method does not follow symbolic references, even if applicable for
the subclass.

Note: This method unconditionally deletes the contents of a reference.
    To delete atomically only if the reference has not changed, use
    remove_if_equals().

Args:
  name: The refname to delete.
N)rS   rG   s     r   __delitem__RefsContainer.__delitem__  s     	dD)r   c                     0 nU R                  5        H"  n [        U R                  U5      5      nX1U'   M$     U$ ! [         a     M5  f = f)zeGet a dict with all symrefs in this container.

Returns: Dictionary mapping source ref to target ref
)r[   r   ru   r   )r+   ri   srcdsts       r   get_symrefsRefsContainer.get_symrefs  sU    
 <<>C(s);< C " 
	  s   ;
A	A	c                 ,    [        U R                  5      e)zwWatch for changes to the refs in this container.

Returns a context manager that yields tuples with (refname, new_sha)
)r:   watchrB   s    r   r   RefsContainer.watch  s    
 "$**--r   r)   r(   NNNN)NNNNF)__name__
__module____qualname____firstlineno____doc__r-   r7   r;   rA   rH   rX   r[   r_   rb   rL   rk   rp   ru   rs   r}   r   r   r   rO   r   r   rS   r   r   r   __static_attributes__rF   r   r   r%   r%   _   s     U( 9$8	 Q:0$" '$7"(
(
 643,( 90*.r   r%   c                   2    \ rS rSrS rS rS rS rS rSr	g)	_DictRefsWatcheri  c                     Xl         g r(   )_refs)r+   refss     r   r-   _DictRefsWatcher.__init__  s    
r   c                 t    SSK Jn  U" 5       U l         U R                  R                  R	                  U 5        U $ )Nr   Queue)queuer   r   	_watchersrN   )r+   r   s     r   	__enter___DictRefsWatcher.__enter__  s+    W


  &r   c                 6    U R                   R                  5       $ r(   r   rt   rB   s    r   __next___DictRefsWatcher.__next__      zz~~r   c                 :    U R                   R                  U5        g r(   )r   
put_nowait)r+   entrys     r   _notify_DictRefsWatcher._notify  s    

e$r   c                 N    U R                   R                  R                  U 5        gNF)r   r   rQ   r+   exc_typeexc_valexc_tbs       r   __exit___DictRefsWatcher.__exit__  s    

##D)r   )r   r   N)
r   r   r   r   r-   r   r   r   r   r   rF   r   r   r   r     s     %r   r   c                      ^  \ rS rSrSrSU 4S jjrS rS rS rS r	S r
    SS	 jr    SS
 jr    SS jr    SS jrS rS rS rSrU =r$ )DictRefsContaineri  z}RefsContainer backed by a simple dict.

This container does not support symbolic or packed references and is not
threadsafe.
c                 `   > [         [        U ]  US9  Xl        0 U l        [        5       U l        g )Nr,   )superr   r-   r   _peeledrK   r   )r+   r   r,   	__class__s      r   r-   DictRefsContainer.__init__  s+    /v/>
r   c                 6    U R                   R                  5       $ r(   r   rb   rB   s    r   r[   DictRefsContainer.allkeys      zz  r   c                 :    U R                   R                  US 5      $ r(   r   rt   rG   s     r   rs    DictRefsContainer.read_loose_ref      zz~~dD))r   c                     0 $ r(   rF   rB   s    r   rA   !DictRefsContainer.get_packed_refs      	r   c                 N    U R                    H  nUR                  X45        M     g r(   )r   r   )r+   r0   newshawatchers       r   r   DictRefsContainer._notify  s    ~~GOOSM* &r   c                     [        U 5      $ r(   )r   rB   s    r   r   DictRefsContainer.watch  s    %%r   c           
          U R                  U5      S   n[        U-   nXR                  U'   U R                  X5        U R	                  UUUUUUUS9  g )Nr   r3   r4   r5   r6   )r}   r   r   r   r7   )	r+   r<   r=   r3   r4   r5   r6   oldnews	            r   r;   "DictRefsContainer.set_symbolic_ref  s^     kk$#un

4T		 	 	
r   c                 L   Ub%  U R                   R                  U[        5      U:w  a  gU R                  U5      u  pU Hc  n
U R	                  U
5        U R                   R                  U
5      nX0R                   U
'   U R                  X5        U R                  U
UUUUUUS9  Me     gNFr   T)r   rt   r   r}   rp   r   r7   )r+   r<   r   r   r3   r4   r5   r6   	realnamesr   realnamer   s               r   rO   DictRefsContainer.set_if_equals   s     4::>>$#AW#L{{4(	!H)**..*C#*JJx LL+II##!   " r   c           
          XR                   ;   a  gX R                   U'   U R                  X5        U R                  US UUUUUS9  gr   )r   r   r7   )r+   r<   r0   r3   r4   r5   r6   s          r   r   DictRefsContainer.add_if_new  sT     ::

4T		 	 	
 r   c           
          Ub%  U R                   R                  U[        5      U:w  a  g U R                   R                  U5      nU R	                  US 5        U R                  UUS UUUUS9  g! [         a     gf = fr   )r   rt   r   popr   r7   rR   )r+   r<   r   r3   r4   r5   r6   r   s           r   rS   "DictRefsContainer.remove_if_equals5  s     4::>>$#AW#L	**..&C LLt$II##!     	 	s   A- -
A:9A:c                 8    U R                   R                  U5      $ r(   )r   rt   rG   s     r   rH   DictRefsContainer.get_peeledQ  s    ||%%r   c                 \    UR                  5        H  u  p#U R                  USU5        M     g)z0Update multiple refs; intended only for testing.N)rM   rO   )r+   r   r0   r   s       r   _updateDictRefsContainer._updateT  s(     

HCsD#. %r   c                 :    U R                   R                  U5        g)z5Update cached peeled refs; intended only for testing.N)r   update)r+   peeleds     r   _update_peeled DictRefsContainer._update_peeled[  s    F#r   )r   r   r   r(   r   )r   r   r   r   r   r-   r[   rs   rA   r   r   r;   rO   r   rS   rH   r   r   r   __classcell__r   s   @r   r   r     s    !*+& 
8 B 8 8&/$ $r   r   c                   6    \ rS rSrSrS rS rS rS rS r	Sr
g	)
InfoRefsContaineri`  z5Refs container that reads refs from a info/refs file.c                    0 U l         0 U l        UR                  5        H  nUR                  S5      R	                  S5      u  p4UR                  [        5      (       a3  US S n[        U5      (       d  [        SU-  5      eX0R                  U'   Mr  [        U5      (       d  [        SU-  5      eX0R                   U'   M     g )N   
   	invalid ref name %r)	r   r   	readlinesr   splitr   ANNOTATED_TAG_SUFFIXr#   r   )r+   fliner   r<   s        r   r-   InfoRefsContainer.__init__c  s    
KKMDE*007IC}}122CRy'--$%:T%ABB%(T"'--$%:T%ABB#&

4  "r   c                 6    U R                   R                  5       $ r(   r   rB   s    r   r[   InfoRefsContainer.allkeysr  r   r   c                 :    U R                   R                  US 5      $ r(   r   rG   s     r   rs    InfoRefsContainer.read_loose_refu  r   r   c                     0 $ r(   rF   rB   s    r   rA   !InfoRefsContainer.get_packed_refsx  r   r   c                 `     U R                   U   $ ! [         a    U R                  U   s $ f = fr(   )r   rR   r   rG   s     r   rH   InfoRefsContainer.get_peeled{  s4    	$<<%% 	$::d##	$s    --)r   r   N)r   r   r   r   r   r-   r[   rs   rA   rH   r   rF   r   r   r   r   `  s    ?'!*$r   r   c                   2    \ rS rSrS rS rS rS rS rSr	g)	_InotifyRefsWatcheri  c                 v   SS K nSSKJn  [        R                  " U5      U l        UR                  5       U l        U R                  R                  U R
                  UR                  UR                  -  UR                  -  SSS9  UR                  U R                  U R                  S9U l        U" 5       U l        g )Nr   r   T)recauto_add)default_proc_fun)	pyinotifyr   r   osfsdecodepathWatchManagermanager	add_watch	IN_DELETEIN_CLOSE_WRITEIN_MOVED_TOThreadedNotifierr   notifier)r+   r  r  r   s       r   r-   _InotifyRefsWatcher.__init__  s    KK%	 --/II)":"::Y=R=RR	 	 	
 "22LL4<< 3 
 W
r   c                 N   UR                   (       a  g UR                  R                  S5      (       a  g [        R                  " [        R
                  R                  UR                  U R
                  5      5      nUR                  S:X  a  U R                  R                  US 45        g UR                  S;   a[  [        UR                  S5       nUR                  5       R                  S5      nU R                  R                  X$45        S S S 5        g g ! , (       d  f       g = f)Nz.lockr!  )r"  r#  rb   
)dirpathnamer   r  fsencoder  relpathmasknamer   r   openreadliner   )r+   eventr0   r	  r   s        r   r   _InotifyRefsWatcher._notify  s    99>>""7++kk"''//%..$))DE>>[(JJ!!3+.^^@@ennd+qjjl))'2

%%sj1 ,+ A++s   <D
D$c                 6    U R                   R                  5       $ r(   r   rB   s    r   r   _InotifyRefsWatcher.__next__  r   r   c                 :    U R                   R                  5         U $ r(   )r%  startrB   s    r   r   _InotifyRefsWatcher.__enter__  s    r   c                 8    U R                   R                  5         gr   )r%  stopr   s       r   r   _InotifyRefsWatcher.__exit__  s    r   )r  r%  r  r   N)
r   r   r   r   r-   r   r   r   r   r   rF   r   r   r  r    s    $2 r   r  c                      ^  \ rS rSrSrSU 4S jjrS rS rS rS r	S r
S	 rS
 rS r    SS jr    SS jr    SS jr    SS jrS rSrU =r$ )DiskRefsContaineri  z)Refs container that reads refs from disk.c                    > [         [        U ]  US9  [        USS 5      b  [        R
                  " U5      nXl        Uc  Un[        USS 5      b  [        R
                  " U5      nX l        S U l        S U l	        g )Nr   encode)
r   r<  r-   getattrr  r,  r  worktree_path_packed_refs_peeled_refs)r+   r  r@  r,   r   s       r   r-   DiskRefsContainer.__init__  sv    /v/>44(4;;t$D	  M=(D1=KK6M*  r   c                 R    U R                   R                  < SU R                  < S3$ )N())r   r   r  rB   s    r   __repr__DiskRefsContainer.__repr__  s    >>22DII>>r   c                    [        5       nU R                  U5      n[        R                  " U5       H  u  pEnU[	        U5      S  n[        R
                  R                  S:w  a>  UR                  [        R                  " [        R
                  R                  5      S5      nUR                  S5      nU HK  nSR                  U(       a  U/O/ U/-   5      n	[        US-   U	-   5      (       d  M:  UR                  U	5        MM     M     U R                  5        HG  n
U
R                  U5      (       d  M  UR                  U
[	        U5      S  R                  S5      5        MI     U$ )N/r   )rK   refpathr  walkr   r  sepreplacer,  rh   rP   r#   rN   rA   r   )r+   rT   rL   r  rootunused_dirsfilesr*  filenamer    rj   s              r   rL   DiskRefsContainer.subkeys  s   %||D!(*$Dus4y{#Cww{{c!kk"++bggkk":DA))D/C!))ccUrhZ$GH $D4K'$9::KK( " )6 '')C~~d##CD	,22489 * r   c                    [        5       n[        R                  R                  U R	                  S5      5      (       a  UR                  S5        U R	                  S5      nU R	                  S5      n[        R                  " U5       H  u  pEnU[        U5      S  n[        R                  R                  S:w  a>  UR                  [        R                  " [        R                  R                  5      S5      nU H8  nSR                  Xx/5      n	[        U	5      (       d  M'  UR                  U	5        M:     M     UR                  U R                  5       5        U$ )Nrn   r   s   refsrJ  r   )rK   r  r  existsrK  rN   rL  r   rM  rN  r,  rP   r#   r   rA   )
r+   r[   r  refspathrO  rP  rQ  r*  rR  r    s
             r   r[   DiskRefsContainer.allkeys  s    %77>>$,,w/00KK ||C <<((*(9$Dus4y{#Cww{{c!kk"++bggkk":DA!))SO4#G,,KK( "	 ): 	t++-.r   c                 n   [         R                  R                  S:w  a>  UR                  S[         R                  " [         R                  R                  5      5      nUS:X  a*  [         R                  R                  U R                  U5      $ [         R                  R                  U R                  U5      $ )zReturn the disk path of a ref.rJ  r   rn   )r  r  rM  rN  r,  rP   r@  rG   s     r   rK  DiskRefsContainer.refpath  sp    77;;#<<bkk"''++&>?D 7?77<< 2 2D9977<<		400r   c                    U R                   Gc  0 U l         0 U l        [        R                  R	                  U R                  S5      n [        US5      nU   [        [        U5      5      R                  5       nUR                  S5      (       aA  SU;   a;  [        U5       H+  u  pEnX@R                   U'   U(       d  M  X`R                  U'   M-     O3UR                  S5        [        U5       H  u  pEX@R                   U'   M     SSS5        U R                   $ U R                   $ ! [         a    0 s $ f = f! , (       d  f       U R                   $ = f)r@   N   packed-refsr(  s   # pack-refss    peeledr   )rA  rB  r  r  rP   r   FileNotFoundErrornextr^   r   r   read_packed_refs_with_peeledseekread_packed_refs)r+   r  r	  
first_liner   r<   r   s          r   rA   !DiskRefsContainer.get_packed_refs  s(    $ !#D "D77<<		>:DD$' !$q']113
((88Z:=U-I!-L)625))$/!66<--d3 .M
 FF1I%5a%8	25))$/ &9     t    % 	    s&   D# A#D5=AD5#D21D25
Ec                     U R                  5         U R                  b  XR                  ;  a  gXR                  ;   a  U R                  U   $ X   $ rE   )rA   rB  rA  rG   s     r   rH   DiskRefsContainer.get_peeled  sQ     	$4E4E(E$$$$$T** :r   c                    U R                  U5      n [        US5       nUR                  [        [        5      5      nU[        :X  a/  U[        [        U5      5      R                  S5      -   sSSS5        $ XCR                  S[        [        5      -
  5      -   sSSS5        $ ! , (       d  f       g= f! [        [        [        4 a     gf = f)a_  Read a reference file and return its contents.

If the reference file a symbolic reference, only read the first line of
the file. Otherwise, only read the first 40 bytes.

Args:
  name: the refname to read, relative to refpath
Returns: The contents of the ref file, or None if the file does not
    exist.
Raises:
  IOError: if any other error occurs
r(  r   N(   )rK  r   readr   r   r]  r^   r   r\  IsADirectoryErrorNotADirectoryError)r+   r<   rR  r	  headers        r   rs    DiskRefsContainer.read_loose_ref#  s     <<%
	4(AF,V#!DaM$8$8$AA	 )( "FF2F+;$<< )(( "#46HI 		s;   B4 AB#-	B4 7"B#	B4 #
B1-B4 1B4 4CCc                    U R                   c  g [        R                  R                  U R                  S5      n[	        US5      n S U l         U R                  5         XR                   ;  a   UR                  5         g U R                   U	 XR                  ;   a  U R                  U	 [        X0R                   U R                  5        UR                  5         UR                  5         g ! UR                  5         f = f)Nr[  wb)
rA  r  r  rP   r   rA   abortrB  write_packed_refsclose)r+   r<   rR  r	  s       r   _remove_packed_ref$DiskRefsContainer._remove_packed_ref=  s    $77<<		>:Hd#	 $D  ",,, GGI !!$'(((%%d+a!2!2D4E4EFGGIGGIAGGIs   &C( >AC( (C:c           
      j   U R                  U5        U R                  U5        U R                  U5      n[        US5      n UR                  [        U-   S-   5        U R                  U5      S   n	U R                  UU	U	UUUUS9  UR                  5         g! [         a    UR                  5         e f = f)zMake a ref point at another ref.

Args:
  name: Name of the ref to set
  other: Name of the ref to point at
  message: Optional message to describe the change
rm  r  r   r   N)
rp   rK  r   writer   r}   r7   rp  BaseExceptionrn  )
r+   r<   r=   r3   r4   r5   r6   rR  r	  r   s
             r   r;   "DiskRefsContainer.set_symbolic_refR  s      	D!E"<<%Hd#	GGFUNU*+++d#B'CII##!   GGI	  	GGI	s   AB B2c                    U R                  U5         U R                  U5      u  pUS   n
U R	                  U
5      n[
        R                  R                  U
5      nU R                  5       nU(       aF  UR                  US5      b  [        U5      e[
        R                  R                  U5      nU(       a  MF  [        [
        R                  R                  U5      5        [        US5       nUbY   U R                  U
5      nUc$  U R                  5       R                  U
[        5      nX:w  a  UR                  5          SSS5        g  UR%                  US-   5        U R'                  U
UUUUUUS9  SSS5        g! [        [        4 a    Un
 GNff = f! [         ["        4 a    UR                  5         e f = f! [         ["        4 a    UR                  5         e f = f! , (       d  f       g= f)a  Set a refname to new_ref only if it currently equals old_ref.

This method follows all symbolic references, and can be used to perform
an atomic compare-and-swap operation.

Args:
  name: The refname to set.
  old_ref: The old sha the refname must refer to, or None to set
    unconditionally.
  new_ref: The new sha the refname will refer to.
  message: Set message for reflog
Returns: True if the set was successful, False otherwise.
r   Nrm  Fr  r   T)rp   r}   rR   
IndexErrorrK  r  r  dirnamerA   rt   ri  r	   r   rs   r   rn  OSErrorIOErrorrt  r7   )r+   r<   r   r   r3   r4   r5   r6   r   r   r   rR  	probe_refpacked_refsr	  orig_refs                   r   rO   DiskRefsContainer.set_if_equalsx  s   . 	D!	;;t,LI }H <<) GGOOH-	**,y$/;(22	2I i
 	"''//(34Xt$"
#228<H'#'#7#7#9#=#=h#Q*	$ %$ +%( II##!  % %6 Q *% 	H	.  ) GGI
 W% 	 %$6 sN   E< ,G1AFG
F:G<FF"F77G:"GG
G-c                     U R                  U5      u  pxUb  gUS   n	U R                  U	5        U R	                  U	5      n
[        [        R                  R                  U
5      5        [        U
S5       n[        R                  R                  U
5      (       d  XR                  5       ;   a  UR                  5          SSS5        g UR                  US-   5        U R                  USUUUUUS9   SSS5        g! [        [        4 a    Un	 Nf = f! [        [         4 a    UR                  5         e f = f! , (       d  f       g= f)aG  Add a new reference only if it does not already exist.

This method follows symrefs, and only ensures that the last ref in the
chain does not exist.

Args:
  name: The refname to set.
  ref: The new sha the refname will refer to.
  message: Optional message for reflog
Returns: True if the add was successful, False otherwise.
NFr   rm  r  r   T)r}   rR   rx  rp   rK  r	   r  r  ry  r   rU  rA   rn  rt  r7   rz  r{  )r+   r<   r0   r3   r4   r5   r6   r   r   r   rR  r	  s               r   r   DiskRefsContainer.add_if_new  s/   (	"&++d"3I# }H 	H%<<)"''//(34Xt$ww~~h''43G3G3I+I	 %$e$
 		''%#   %& 1 *% 	H	 W% 	 %$& s;   C: C: 4A	D7DD7:DD"D44D77
Ec           
         U R                  U5        U R                  U5      n[        [        R                  R                  U5      5        [        US5      n UbO  U R                  U5      n	U	c$  U R                  5       R                  U[        5      n	X:w  a   UR                  5         g [        R                  " U5        U R                  U5        U R                  UUSUUUUS9  UR                  5         Un
  U
R!                  SS5      u  pU R                  U
5      n [        R$                  " U5        M?  ! [         a     Nf = f! UR                  5         f = f! ["         a     gf = f! [&         a     gf = f)a  Remove a refname only if it currently equals old_ref.

This method does not follow symbolic references. It can be used to
perform an atomic compare-and-delete operation.

Args:
  name: The refname to delete.
  old_ref: The old sha the refname must refer to, or None to
    delete unconditionally.
  message: Optional message
Returns: True if the delete was successful, False otherwise.
rm  NFr   Tr   r   )rp   rK  r	   r  r  ry  r   rs   rA   rt   r   rn  rQ   r\  rq  r7   rsplitr   rmdirrz  )r+   r<   r   r3   r4   r5   r6   rR  r	  r~  parentr   parent_filenames                r   rS   "DiskRefsContainer.remove_if_equals  sz   * 	D!<<%"''//(34Hd#	"..t4##33599$IH& ( GGI#		(# ##D)II##!   GGI
 "MM$2	 #ll62O) + %  GGI     
 sU   A E	 +D9 &E	 ;E !E. 9
EE	 EE	 	E
E+*E+.
E;:E;c                 4    SS K n[        U R                  5      $ )Nr   )r  r  r  )r+   r  s     r   r   DiskRefsContainer.watch;  s    "499--r   )rA  rB  r  r@  )NNr   )r   r   r   r   r   r-   rG  rL   r[   rK  rA   rH   rs   rq  r;   rO   r   rS   r   r   r   r   s   @r   r<  r<    s    3!?&"	1!@&42 $V CR 1n IV. .r   r<  c                    U R                  S5      R                  S5      n[        U5      S:w  a  [        SU -  5      eUu  p#[	        U5      (       d  [        SU-  5      e[        U5      (       d  [        SU-  5      eX#4$ )z6Split a single ref line into a tuple of SHA1 and name.r)         zinvalid ref line %rInvalid hex sha %rr  )r   r  r   r   r   r#   )r
  fieldsr   r<   s       r   _split_ref_liner  A  s    [[!''-F
6{a!"7$">??IC!"6"<==D!!!"7$">??;r   c              #      #    U  HI  nUR                  S5      (       a  M  UR                  S5      (       a  [        S5      e[        U5      v   MK     g7f)z{Read a packed refs file.

Args:
  f: file-like object to read from
Returns: Iterator over tuples with SHA1s and ref names.
   #   ^z.found peeled ref in packed-refs without peeledN)r   r   r  )r	  r
  s     r   r`  r`  N  sI      ??4  ??4  %&VWWd## s   AAc              #     #    SnU  H  nUS   S:X  a  M  UR                  S5      nUR                  S5      (       aP  U(       d  [        S5      e[        USS 5      (       d  [        SUSS -  5      e[	        U5      u  p4SnX4USS 4v   M  U(       a  [	        U5      u  p4X4S4v   UnM     U(       a  [	        U5      u  p4X4S4v   gg7f)	zRead a packed refs file including peeled refs.

Assumes the "# pack-refs with: peeled" line was already read. Yields tuples
with ref names, SHA1s, and peeled SHA1s (or None).

Args:
  f: file-like object to read from, seek'ed to the second line
Nr   r  r   r  zunexpected peeled ref liner   r  )r   r   r   r   r  )r	  lastr
  r   r<   s        r   r^  r^  ^  s      D7d?{{7#??4  )*FGGQR)))*>ab*IJJ'-ICDd12h''+D1	$''D! " #D)	$ s   CCc                     Uc  0 nOU R                  S5        [        UR                  5       5       H@  nU R                  [        X   U5      5        X2;   d  M'  U R                  SX#   -   S-   5        MB     g)zWrite a packed refs file.

Args:
  f: empty file-like object to write to
  packed_refs: dict of refname to sha of packed refs to write
  peeled_refs: dict of refname to peeled value of sha
Ns   # pack-refs with: peeled
r  r  )rt  sortedrb   r   )r	  r}  peeled_refsr    s       r   ro  ro  ~  si     	-.+**,-	-w78!GGD;//%78 .r   c                     0 nU R                  5        H*  nUR                  S5      R                  SS5      u  p4X1U'   M,     U$ )Nr   r  r   )r  r   r  )r	  ri   r
  r   r<   s        r   read_info_refsr    sB    
Ckk'*00:D	  Jr   c              #   P  #    [        U R                  5       5       Ht  u  p#US:X  a  M   X   nUR                  U5      nUR                  S-   U-   S-   v   UR                  UR                  :w  d  MV  UR                  S-   U-   [
        -   S-   v   Mv     g! [         a     M  f = f7f)zGenerate info refs.rn   r  r  N)r  rM   rR   peel_shaidr  )r   storer<   r   or   s         r   write_info_refsr    s     DJJL)	 7?	
A $ddUlT!E))44699))e#d*-AAEII *  		s.   'B&BA B&2#B&
B#B&"B##B&c                 ,    U R                  [        5      $ r(   )r   LOCAL_BRANCH_PREFIX)xs    r   is_local_branchr    s    <<+,,r   c                     U R                  5        VVs0 s H#  u  pUR                  [        5      (       a  M!  X_M%     snn$ s  snnf )zRemove all peeled refs)rM   r   r  )r   r0   r   s      r   strip_peeled_refsr    sB     **,&JS||01 	&  s
    AAr(   )#r   r  dulwich.errorsr   r   dulwich.objectsr   r   r   dulwich.filer   r	   r   r  LOCAL_TAG_PREFIXrK   r   r  r   r#   objectr%   r   r   r   r  r<  r  r`  r^  ro  r  r  r  r  rF   r   r   <module>r     s   , 
 
 
$   N# 	DT.F T.n
v ,Q$ Q$h$ $D)& )XP. P.f
$  @9$J"-r   