��c@sdZddlZddlZddlmZdZedZdZedZeeZ e dZ
e
ddZd �Zd
�Z
d�Zd�Zd
�Zged�D]Zee�^q�Zd�Zd�Zd�Zd�Zdefd��YZdS(s3
A "pvec" is a changeset property based on the theory of vector clocks
that can be compared to discover relatedness without consulting a
graph. This can be useful for tasks like determining how a
disconnected patch relates to a repository.
Currently a pvec consist of 448 bits, of which 24 are 'depth' and the
remainder are a bit vector. It is represented as a 70-character base85
string.
Construction:
- a root changeset has a depth of 0 and a bit vector based on its hash
- a normal commit has a changeset where depth is increased by one and
one bit vector bit is flipped based on its hash
- a merge changeset pvec is constructed by copying changes from one pvec into
the other to balance its depth
Properties:
- for linear changes, difference in depth is always <= hamming distance
- otherwise, changes are probably divergent
- when hamming distance is < 200, we can reliably detect when pvecs are near
Issues:
- hamming distance ceases to work over distances of ~ 200
- detecting divergence is less accurate when the common ancestor is very close
to either revision or total distance is high
- this could probably be improved by modeling the relation between
delta and hdist
Uses:
- a patch pvec can be used to locate the nearest available common ancestor for
resolving conflicts
- ordering of patches can be established without a DAG
- two head pvecs can be compared to determine whether push/pull/merge is needed
and approximately how many changesets are involved
- can be used to find a heuristic divergence measure between changesets on
different branches
i�N(tnullrevi�iiiicCs/d}x"|D]}|dt|�}q
W|S(sconvert a bytestring to a longii(tord(tbstvtb((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt_bin>s
cCs?d}x2t|�D]$}t|d@�|}|dL}qW|S(Nti�i(txrangetchr(RtlRtp((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt_strEs
cCst|t �t|t�fS(sdepth and bitvec(Rt_depthbytes(R((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt_splitLscCst|t�t|t�S(N(RRt _vecbytes(tdepthtbitvec((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt_joinPscCs8d}x+|r3|d@r&|d7}n|dL}q W|S(Nii((txtc((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt_hweightSs
icCs=||A}d}x&|r8|t|d@7}|dL}qW|S(s+find the hamming distance between two longsii�i(t_htab(taRtdR((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt_hamming\s
cCs�|\}}|\}}||krE||||f\}}}}nt||�}||}|} ||A}
d}||kr�||dd}nd}||}
|
r�G|r�
|@r�| |N} |d8}n|dK}q�Wnt| |�} |
| fS(Nii(Rt_flipbit(RtyRtd1tv1td2tv2thdisttddistRtmtitchangesR((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt _mergeveces*!
cCs t|�d@t}|d|>AS(Nl�i(thasht_vecbits(Rtnodetbit((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyR�scCsR|j}tj|d�s'i|_n|j}|j�|kr)|j}x�t|j�d�D]�}||krb|j|�}|j|�\}}|t kr�dt
|dt �f||<q"|t kr||\}} |dt| |�f||<q"t
|||||�||<qbqbWnt||j��}
ttj|
��S(s3construct a pvec for ctx while filling in the cachet
_pveccacheiii(t_repotutiltsafehasattrR)trevt changelogRR't
parentrevsRRRRR$Rtpvectbase85t b85encode(tctxtrtpvctcltnR'tp1tp2RRR((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pytctxpvec�s$ ! (R0cBsYeZd�Zd�Zd�Zd�Zd�Zd�Zd�Zd�Z d�Z
RS( cCsOt|t�r<||_ttj|��\|_|_nt|�|_dS(N( t
isinstancetstrt_bsR
R1t b85decodet_deptht_vecR:(tselft hashorctx((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt__init__�s $cCs|jS(N(R=(RA((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt__str__�scCs"|j|jko!|j|jkS(N(R@R?(RAR((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt__eq__�scCsC|j|j}|dkr tSt|j|j�|kr?tStS(Ni(R?tFalseRR@tTrue(RARtdelta((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt__lt__�scCs
||kS(N((RAR((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt__gt__�scCs9t|j|j�}t|j|j�|kr5tStS(N(tabsR?RR@RFRG(RARRH((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt__or__�scCs'||Brtd��n|j|jS(Nsconcurrent pvecs(t
ValueErrorR?(RAR((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt__sub__�s
cCs8t|j|j�}t|j|j�}t||�S(N(RKR?RR@tmax(RARRth((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pytdistance�scCsEt|j|j�}|tks=t|j|j�tkrAtSdS(N(RKRR?t_radiusRR@RF(RARtdist((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pytnear�s'(t__name__t
__module__RCRDRERIRJRLRNRQRT(((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyR0�s (t__doc__R1R+R'Rt_sizet_bytest
_depthbitsRRR&RRRRR
RRRRRRR$RR:tobjectR0(((s2/sys/lib/python2.7/site-packages/mercurial/pvec.pyt<module>1s(
% %
|