Mercurial > public > mercurial-scm > hg
annotate rust/hg-core/src/copy_tracing.rs @ 46149:294d5aca4ff5
copies: iterate over children directly (instead of parents)
Before this change we would gather all parent ? child edges and iterate on
all parent, gathering copy information for children and aggregating them from
there.
They are not strict requirement for edges to be processed in that specific
order. We could also simply iterate over all "children" revision and aggregate
data from both parents at the same time. This patch does that.
It make various things simpler:
* since both parents are processed at the same time, we no longer need to
cache data for merge (see next changeset for details),
* we no longer need nested loop to process data,
* we no longer need to store partial merge data for a rev from distinct loop
interaction to another when processing merges,
* we no longer need to build a full parent -> children mapping (we only rely on
a simpler "parent -> number of children" map (for memory efficiency),
* the data access pattern is now simpler (from lower revisions to higher
revisions) and entirely predicable. That predictability open the way to
prefetching and parallel processing.
So that new iterations order requires simpler code and open the way to
interesting optimisation.
The effect on performance is quite good. In the worse case, we don't see any
significant negative impact. And in the best case, the reduction of roundtrip
to Python provide us with a significant speed. Some example below:
Repo Case Source-Rev Dest-Rev # of revisions old time new time Difference Factor time per rev
---------------------------------------------------------------------------------------------------------------------------------------------------------------
mozilla-try x00000_revs_x00000_added_0_copies dc8a3ca7010e d16fde900c9c : 34414 revs, 0.962867 s, 0.502584 s, -0.460283 s, ? 0.5220, 14 ?s/rev
mozilla-try x0000_revs_xx000_added_x_copies 156f6e2674f2 4d0f2c178e66 : 8598 revs, 0.110717 s, 0.076323 s, -0.034394 s, ? 0.6894, 8 ?s/rev
# full comparison between the previous changeset and this one
Repo Case Source-Rev Dest-Rev # of revisions old time new time Difference Factor time per rev
---------------------------------------------------------------------------------------------------------------------------------------------------------------
mercurial x_revs_x_added_0_copies ad6b123de1c7 39cfcef4f463 : 1 revs, 0.000048 s, 0.000041 s, -0.000007 s, ? 0.8542, 41 ?s/rev
mercurial x_revs_x_added_x_copies 2b1c78674230 0c1d10351869 : 6 revs, 0.000153 s, 0.000102 s, -0.000051 s, ? 0.6667, 17 ?s/rev
mercurial x000_revs_x000_added_x_copies 81f8ff2a9bf2 dd3267698d84 : 1032 revs, 0.004209 s, 0.004254 s, +0.000045 s, ? 1.0107, 4 ?s/rev
pypy x_revs_x_added_0_copies aed021ee8ae8 099ed31b181b : 9 revs, 0.000203 s, 0.000282 s, +0.000079 s, ? 1.3892, 31 ?s/rev
pypy x_revs_x000_added_0_copies 4aa4e1f8e19a 359343b9ac0e : 1 revs, 0.000059 s, 0.000048 s, -0.000011 s, ? 0.8136, 48 ?s/rev
pypy x_revs_x_added_x_copies ac52eb7bbbb0 72e022663155 : 7 revs, 0.000194 s, 0.000211 s, +0.000017 s, ? 1.0876, 30 ?s/rev
pypy x_revs_x00_added_x_copies c3b14617fbd7 ace7255d9a26 : 1 revs, 0.000380 s, 0.000375 s, -0.000005 s, ? 0.9868, 375 ?s/rev
pypy x_revs_x000_added_x000_copies df6f7a526b60 a83dc6a2d56f : 6 revs, 0.010588 s, 0.010574 s, -0.000014 s, ? 0.9987, 1762 ?s/rev
pypy x000_revs_xx00_added_0_copies 89a76aede314 2f22446ff07e : 4785 revs, 0.048961 s, 0.049974 s, +0.001013 s, ? 1.0207, 10 ?s/rev
pypy x000_revs_x000_added_x_copies 8a3b5bfd266e 2c68e87c3efe : 6780 revs, 0.083612 s, 0.084300 s, +0.000688 s, ? 1.0082, 12 ?s/rev
pypy x000_revs_x000_added_x000_copies 89a76aede314 7b3dda341c84 : 5441 revs, 0.058579 s, 0.060128 s, +0.001549 s, ? 1.0264, 11 ?s/rev
pypy x0000_revs_x_added_0_copies d1defd0dc478 c9cb1334cc78 : 43645 revs, 0.736783 s, 0.686542 s, -0.050241 s, ? 0.9318, 15 ?s/rev
pypy x0000_revs_xx000_added_0_copies bf2c629d0071 4ffed77c095c : 2 revs, 0.022050 s, 0.009277 s, -0.012773 s, ? 0.4207, 4638 ?s/rev
pypy x0000_revs_xx000_added_x000_copies 08ea3258278e d9fa043f30c0 : 11316 revs, 0.120800 s, 0.114733 s, -0.006067 s, ? 0.9498, 10 ?s/rev
netbeans x_revs_x_added_0_copies fb0955ffcbcd a01e9239f9e7 : 2 revs, 0.000140 s, 0.000081 s, -0.000059 s, ? 0.5786, 40 ?s/rev
netbeans x_revs_x000_added_0_copies 6f360122949f 20eb231cc7d0 : 2 revs, 0.000114 s, 0.000107 s, -0.000007 s, ? 0.9386, 53 ?s/rev
netbeans x_revs_x_added_x_copies 1ada3faf6fb6 5a39d12eecf4 : 3 revs, 0.000224 s, 0.000173 s, -0.000051 s, ? 0.7723, 57 ?s/rev
netbeans x_revs_x00_added_x_copies 35be93ba1e2c 9eec5e90c05f : 9 revs, 0.000723 s, 0.000698 s, -0.000025 s, ? 0.9654, 77 ?s/rev
netbeans x000_revs_xx00_added_0_copies eac3045b4fdd 51d4ae7f1290 : 1421 revs, 0.009665 s, 0.009248 s, -0.000417 s, ? 0.9569, 6 ?s/rev
netbeans x000_revs_x000_added_x_copies e2063d266acd 6081d72689dc : 1533 revs, 0.014820 s, 0.015446 s, +0.000626 s, ? 1.0422, 10 ?s/rev
netbeans x000_revs_x000_added_x000_copies ff453e9fee32 411350406ec2 : 5750 revs, 0.076049 s, 0.074373 s, -0.001676 s, ? 0.9780, 12 ?s/rev
netbeans x0000_revs_xx000_added_x000_copies 588c2d1ced70 1aad62e59ddd : 66949 revs, 0.683603 s, 0.639870 s, -0.043733 s, ? 0.9360, 9 ?s/rev
mozilla-central x_revs_x_added_0_copies 3697f962bb7b 7015fcdd43a2 : 2 revs, 0.000161 s, 0.000088 s, -0.000073 s, ? 0.5466, 44 ?s/rev
mozilla-central x_revs_x000_added_0_copies dd390860c6c9 40d0c5bed75d : 8 revs, 0.000234 s, 0.000199 s, -0.000035 s, ? 0.8504, 24 ?s/rev
mozilla-central x_revs_x_added_x_copies 8d198483ae3b 14207ffc2b2f : 9 revs, 0.000247 s, 0.000171 s, -0.000076 s, ? 0.6923, 19 ?s/rev
mozilla-central x_revs_x00_added_x_copies 98cbc58cc6bc 446a150332c3 : 7 revs, 0.000630 s, 0.000592 s, -0.000038 s, ? 0.9397, 84 ?s/rev
mozilla-central x_revs_x000_added_x000_copies 3c684b4b8f68 0a5e72d1b479 : 3 revs, 0.003286 s, 0.003151 s, -0.000135 s, ? 0.9589, 1050 ?s/rev
mozilla-central x_revs_x0000_added_x0000_copies effb563bb7e5 c07a39dc4e80 : 6 revs, 0.062441 s, 0.061612 s, -0.000829 s, ? 0.9867, 10268 ?s/rev
mozilla-central x000_revs_xx00_added_0_copies 6100d773079a 04a55431795e : 1593 revs, 0.005423 s, 0.005381 s, -0.000042 s, ? 0.9923, 3 ?s/rev
mozilla-central x000_revs_x000_added_x_copies 9f17a6fc04f9 2d37b966abed : 41 revs, 0.005919 s, 0.003742 s, -0.002177 s, ? 0.6322, 91 ?s/rev
mozilla-central x000_revs_x000_added_x000_copies 7c97034feb78 4407bd0c6330 : 7839 revs, 0.062597 s, 0.061983 s, -0.000614 s, ? 0.9902, 7 ?s/rev
mozilla-central x0000_revs_xx000_added_0_copies 9eec5917337d 67118cc6dcad : 615 revs, 0.043551 s, 0.019861 s, -0.023690 s, ? 0.4560, 32 ?s/rev
mozilla-central x0000_revs_xx000_added_x000_copies f78c615a656c 96a38b690156 : 30263 revs, 0.192475 s, 0.188101 s, -0.004374 s, ? 0.9773, 6 ?s/rev
mozilla-central x00000_revs_x0000_added_x0000_copies 6832ae71433c 4c222a1d9a00 : 153721 revs, 1.955575 s, 1.806696 s, -0.148879 s, ? 0.9239, 11 ?s/rev
mozilla-central x00000_revs_x00000_added_x000_copies 76caed42cf7c 1daa622bbe42 : 204976 revs, 2.886501 s, 2.682987 s, -0.203514 s, ? 0.9295, 13 ?s/rev
mozilla-try x_revs_x_added_0_copies aaf6dde0deb8 9790f499805a : 2 revs, 0.001181 s, 0.000852 s, -0.000329 s, ? 0.7214, 426 ?s/rev
mozilla-try x_revs_x000_added_0_copies d8d0222927b4 5bb8ce8c7450 : 2 revs, 0.001189 s, 0.000859 s, -0.000330 s, ? 0.7225, 429 ?s/rev
mozilla-try x_revs_x_added_x_copies 092fcca11bdb 936255a0384a : 4 revs, 0.000563 s, 0.000150 s, -0.000413 s, ? 0.2664, 37 ?s/rev
mozilla-try x_revs_x00_added_x_copies b53d2fadbdb5 017afae788ec : 2 revs, 0.001548 s, 0.001158 s, -0.000390 s, ? 0.7481, 579 ?s/rev
mozilla-try x_revs_x000_added_x000_copies 20408ad61ce5 6f0ee96e21ad : 1 revs, 0.027782 s, 0.027240 s, -0.000542 s, ? 0.9805, 27240 ?s/rev
mozilla-try x_revs_x0000_added_x0000_copies effb563bb7e5 c07a39dc4e80 : 6 revs, 0.062781 s, 0.062824 s, +0.000043 s, ? 1.0007, 10470 ?s/rev
mozilla-try x000_revs_xx00_added_0_copies 6100d773079a 04a55431795e : 1593 revs, 0.005778 s, 0.005463 s, -0.000315 s, ? 0.9455, 3 ?s/rev
mozilla-try x000_revs_x000_added_x_copies 9f17a6fc04f9 2d37b966abed : 41 revs, 0.006192 s, 0.004238 s, -0.001954 s, ? 0.6844, 103 ?s/rev
mozilla-try x000_revs_x000_added_x000_copies 1346fd0130e4 4c65cbdabc1f : 6657 revs, 0.065391 s, 0.064113 s, -0.001278 s, ? 0.9805, 9 ?s/rev
mozilla-try x0000_revs_x_added_0_copies 63519bfd42ee a36a2a865d92 : 40314 revs, 0.317216 s, 0.294063 s, -0.023153 s, ? 0.9270, 7 ?s/rev
mozilla-try x0000_revs_x_added_x_copies 9fe69ff0762d bcabf2a78927 : 38690 revs, 0.303119 s, 0.281493 s, -0.021626 s, ? 0.9287, 7 ?s/rev
mozilla-try x0000_revs_xx000_added_x_copies 156f6e2674f2 4d0f2c178e66 : 8598 revs, 0.110717 s, 0.076323 s, -0.034394 s, ? 0.6894, 8 ?s/rev
mozilla-try x0000_revs_xx000_added_0_copies 9eec5917337d 67118cc6dcad : 615 revs, 0.045739 s, 0.020390 s, -0.025349 s, ? 0.4458, 33 ?s/rev
mozilla-try x0000_revs_xx000_added_x000_copies 89294cd501d9 7ccb2fc7ccb5 : 97052 revs, 3.098021 s, 3.023879 s, -0.074142 s, ? 0.9761, 31 ?s/rev
mozilla-try x0000_revs_x0000_added_x0000_copies e928c65095ed e951f4ad123a : 52031 revs, 0.771480 s, 0.735549 s, -0.035931 s, ? 0.9534, 14 ?s/rev
mozilla-try x00000_revs_x_added_0_copies 6a320851d377 1ebb79acd503 : 363753 revs, 18.813422 s, 18.568900 s, -0.244522 s, ? 0.9870, 51 ?s/rev
mozilla-try x00000_revs_x00000_added_0_copies dc8a3ca7010e d16fde900c9c : 34414 revs, 0.962867 s, 0.502584 s, -0.460283 s, ? 0.5220, 14 ?s/rev
mozilla-try x00000_revs_x_added_x_copies 5173c4b6f97c 95d83ee7242d : 362229 revs, 18.684923 s, 18.356645 s, -0.328278 s, ? 0.9824, 50 ?s/rev
mozilla-try x00000_revs_x000_added_x_copies 9126823d0e9c ca82787bb23c : 359344 revs, 18.296305 s, 18.250393 s, -0.045912 s, ? 0.9975, 50 ?s/rev
mozilla-try x00000_revs_x0000_added_x0000_copies 8d3fafa80d4b eb884023b810 : 192665 revs, 3.061887 s, 2.792459 s, -0.269428 s, ? 0.9120, 14 ?s/rev
mozilla-try x00000_revs_x00000_added_x0000_copies 1b661134e2ca 1ae03d022d6d : 228985 revs, 103.869641 s, 107.697264 s, +3.827623 s, ? 1.0369, 470 ?s/rev
mozilla-try x00000_revs_x00000_added_x000_copies 9b2a99adc05e 8e29777b48e6 : 382065 revs, 64.262957 s, 63.961040 s, -0.301917 s, ? 0.9953, 167 ?s/rev
Differential Revision: https://phab.mercurial-scm.org/D9422
author | Pierre-Yves David <pierre-yves.david@octobus.net> |
---|---|
date | Mon, 14 Dec 2020 11:32:24 +0100 |
parents | 818502d2f5e3 |
children | c6bc77f7e593 |
rev | line source |
---|---|
45973
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
1 use crate::utils::hg_path::HgPath; |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
2 use crate::utils::hg_path::HgPathBuf; |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
3 use crate::Revision; |
46149
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
4 use crate::NULL_REVISION; |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
5 |
45971
cc759d3db1e8
copies-rust: leverage the immutability for efficient update
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45964
diff
changeset
|
6 use im_rc::ordmap::DiffItem; |
45963
0d99778af68a
copies-rust: use immutable "OrdMap" to store copies information
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45944
diff
changeset
|
7 use im_rc::ordmap::OrdMap; |
0d99778af68a
copies-rust: use immutable "OrdMap" to store copies information
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45944
diff
changeset
|
8 |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
9 use std::cmp::Ordering; |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
10 use std::collections::HashMap; |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
11 use std::convert::TryInto; |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
12 |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
13 pub type PathCopies = HashMap<HgPathBuf, HgPathBuf>; |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
14 |
46129
818502d2f5e3
copies-rust: pre-introduce a PathToken type and use it where applicable
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46128
diff
changeset
|
15 type PathToken = HgPathBuf; |
818502d2f5e3
copies-rust: pre-introduce a PathToken type and use it where applicable
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46128
diff
changeset
|
16 |
45971
cc759d3db1e8
copies-rust: leverage the immutability for efficient update
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45964
diff
changeset
|
17 #[derive(Clone, Debug, PartialEq)] |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
18 struct TimeStampedPathCopy { |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
19 /// revision at which the copy information was added |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
20 rev: Revision, |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
21 /// the copy source, (Set to None in case of deletion of the associated |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
22 /// key) |
46129
818502d2f5e3
copies-rust: pre-introduce a PathToken type and use it where applicable
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46128
diff
changeset
|
23 path: Option<PathToken>, |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
24 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
25 |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
26 /// maps CopyDestination to Copy Source (+ a "timestamp" for the operation) |
46129
818502d2f5e3
copies-rust: pre-introduce a PathToken type and use it where applicable
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46128
diff
changeset
|
27 type TimeStampedPathCopies = OrdMap<PathToken, TimeStampedPathCopy>; |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
28 |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
29 /// hold parent 1, parent 2 and relevant files actions. |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
30 pub type RevInfo<'a> = (Revision, Revision, ChangedFiles<'a>); |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
31 |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
32 /// represent the files affected by a changesets |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
33 /// |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
34 /// This hold a subset of mercurial.metadata.ChangingFiles as we do not need |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
35 /// all the data categories tracked by it. |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
36 /// This hold a subset of mercurial.metadata.ChangingFiles as we do not need |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
37 /// all the data categories tracked by it. |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
38 pub struct ChangedFiles<'a> { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
39 nb_items: u32, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
40 index: &'a [u8], |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
41 data: &'a [u8], |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
42 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
43 |
45973
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
44 /// Represent active changes that affect the copy tracing. |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
45 enum Action<'a> { |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
46 /// The parent ? children edge is removing a file |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
47 /// |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
48 /// (actually, this could be the edge from the other parent, but it does |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
49 /// not matters) |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
50 Removed(&'a HgPath), |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
51 /// The parent ? children edge introduce copy information between (dest, |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
52 /// source) |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
53 Copied(&'a HgPath, &'a HgPath), |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
54 } |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
55 |
45975
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
56 /// This express the possible "special" case we can get in a merge |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
57 /// |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
58 /// See mercurial/metadata.py for details on these values. |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
59 #[derive(PartialEq)] |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
60 enum MergeCase { |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
61 /// Merged: file had history on both side that needed to be merged |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
62 Merged, |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
63 /// Salvaged: file was candidate for deletion, but survived the merge |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
64 Salvaged, |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
65 /// Normal: Not one of the two cases above |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
66 Normal, |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
67 } |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
68 |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
69 type FileChange<'a> = (u8, &'a HgPath, &'a HgPath); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
70 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
71 const EMPTY: &[u8] = b""; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
72 const COPY_MASK: u8 = 3; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
73 const P1_COPY: u8 = 2; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
74 const P2_COPY: u8 = 3; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
75 const ACTION_MASK: u8 = 28; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
76 const REMOVED: u8 = 12; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
77 const MERGED: u8 = 8; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
78 const SALVAGED: u8 = 16; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
79 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
80 impl<'a> ChangedFiles<'a> { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
81 const INDEX_START: usize = 4; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
82 const ENTRY_SIZE: u32 = 9; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
83 const FILENAME_START: u32 = 1; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
84 const COPY_SOURCE_START: u32 = 5; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
85 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
86 pub fn new(data: &'a [u8]) -> Self { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
87 assert!( |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
88 data.len() >= 4, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
89 "data size ({}) is too small to contain the header (4)", |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
90 data.len() |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
91 ); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
92 let nb_items_raw: [u8; 4] = (&data[0..=3]) |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
93 .try_into() |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
94 .expect("failed to turn 4 bytes into 4 bytes"); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
95 let nb_items = u32::from_be_bytes(nb_items_raw); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
96 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
97 let index_size = (nb_items * Self::ENTRY_SIZE) as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
98 let index_end = Self::INDEX_START + index_size; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
99 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
100 assert!( |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
101 data.len() >= index_end, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
102 "data size ({}) is too small to fit the index_data ({})", |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
103 data.len(), |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
104 index_end |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
105 ); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
106 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
107 let ret = ChangedFiles { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
108 nb_items, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
109 index: &data[Self::INDEX_START..index_end], |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
110 data: &data[index_end..], |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
111 }; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
112 let max_data = ret.filename_end(nb_items - 1) as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
113 assert!( |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
114 ret.data.len() >= max_data, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
115 "data size ({}) is too small to fit all data ({})", |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
116 data.len(), |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
117 index_end + max_data |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
118 ); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
119 ret |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
120 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
121 |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
122 pub fn new_empty() -> Self { |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
123 ChangedFiles { |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
124 nb_items: 0, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
125 index: EMPTY, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
126 data: EMPTY, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
127 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
128 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
129 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
130 /// internal function to return an individual entry at a given index |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
131 fn entry(&'a self, idx: u32) -> FileChange<'a> { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
132 if idx >= self.nb_items { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
133 panic!( |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
134 "index for entry is higher that the number of file {} >= {}", |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
135 idx, self.nb_items |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
136 ) |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
137 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
138 let flags = self.flags(idx); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
139 let filename = self.filename(idx); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
140 let copy_idx = self.copy_idx(idx); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
141 let copy_source = self.filename(copy_idx); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
142 (flags, filename, copy_source) |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
143 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
144 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
145 /// internal function to return the filename of the entry at a given index |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
146 fn filename(&self, idx: u32) -> &HgPath { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
147 let filename_start; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
148 if idx == 0 { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
149 filename_start = 0; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
150 } else { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
151 filename_start = self.filename_end(idx - 1) |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
152 } |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
153 let filename_end = self.filename_end(idx); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
154 let filename_start = filename_start as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
155 let filename_end = filename_end as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
156 HgPath::new(&self.data[filename_start..filename_end]) |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
157 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
158 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
159 /// internal function to return the flag field of the entry at a given |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
160 /// index |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
161 fn flags(&self, idx: u32) -> u8 { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
162 let idx = idx as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
163 self.index[idx * (Self::ENTRY_SIZE as usize)] |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
164 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
165 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
166 /// internal function to return the end of a filename part at a given index |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
167 fn filename_end(&self, idx: u32) -> u32 { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
168 let start = (idx * Self::ENTRY_SIZE) + Self::FILENAME_START; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
169 let end = (idx * Self::ENTRY_SIZE) + Self::COPY_SOURCE_START; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
170 let start = start as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
171 let end = end as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
172 let raw = (&self.index[start..end]) |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
173 .try_into() |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
174 .expect("failed to turn 4 bytes into 4 bytes"); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
175 u32::from_be_bytes(raw) |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
176 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
177 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
178 /// internal function to return index of the copy source of the entry at a |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
179 /// given index |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
180 fn copy_idx(&self, idx: u32) -> u32 { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
181 let start = (idx * Self::ENTRY_SIZE) + Self::COPY_SOURCE_START; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
182 let end = (idx + 1) * Self::ENTRY_SIZE; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
183 let start = start as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
184 let end = end as usize; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
185 let raw = (&self.index[start..end]) |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
186 .try_into() |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
187 .expect("failed to turn 4 bytes into 4 bytes"); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
188 u32::from_be_bytes(raw) |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
189 } |
45973
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
190 |
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
191 /// Return an iterator over all the `Action` in this instance. |
46058
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
192 fn iter_actions(&self, parent: Parent) -> ActionsIterator { |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
193 ActionsIterator { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
194 changes: &self, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
195 parent: parent, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
196 current: 0, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
197 } |
45973
ed0e1339e4a8
copies-rust: combine the iteration over remove and copies into one
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45972
diff
changeset
|
198 } |
45975
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
199 |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
200 /// return the MergeCase value associated with a filename |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
201 fn get_merge_case(&self, path: &HgPath) -> MergeCase { |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
202 if self.nb_items == 0 { |
45975
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
203 return MergeCase::Normal; |
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
204 } |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
205 let mut low_part = 0; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
206 let mut high_part = self.nb_items; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
207 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
208 while low_part < high_part { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
209 let cursor = (low_part + high_part - 1) / 2; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
210 let (flags, filename, _source) = self.entry(cursor); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
211 match path.cmp(filename) { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
212 Ordering::Less => low_part = cursor + 1, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
213 Ordering::Greater => high_part = cursor, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
214 Ordering::Equal => { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
215 return match flags & ACTION_MASK { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
216 MERGED => MergeCase::Merged, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
217 SALVAGED => MergeCase::Salvaged, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
218 _ => MergeCase::Normal, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
219 }; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
220 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
221 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
222 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
223 MergeCase::Normal |
45975
2367937982ba
copies-rust: encapsulate internal sets on `changes`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45974
diff
changeset
|
224 } |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
225 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
226 |
45972
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
227 /// A struct responsible for answering "is X ancestors of Y" quickly |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
228 /// |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
229 /// The structure will delegate ancestors call to a callback, and cache the |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
230 /// result. |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
231 #[derive(Debug)] |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
232 struct AncestorOracle<'a, A: Fn(Revision, Revision) -> bool> { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
233 inner: &'a A, |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
234 pairs: HashMap<(Revision, Revision), bool>, |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
235 } |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
236 |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
237 impl<'a, A: Fn(Revision, Revision) -> bool> AncestorOracle<'a, A> { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
238 fn new(func: &'a A) -> Self { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
239 Self { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
240 inner: func, |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
241 pairs: HashMap::default(), |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
242 } |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
243 } |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
244 |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
245 /// returns `true` if `anc` is an ancestors of `desc`, `false` otherwise |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
246 fn is_ancestor(&mut self, anc: Revision, desc: Revision) -> bool { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
247 if anc > desc { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
248 false |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
249 } else if anc == desc { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
250 true |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
251 } else { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
252 if let Some(b) = self.pairs.get(&(anc, desc)) { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
253 *b |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
254 } else { |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
255 let b = (self.inner)(anc, desc); |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
256 self.pairs.insert((anc, desc), b); |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
257 b |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
258 } |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
259 } |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
260 } |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
261 } |
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
262 |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
263 struct ActionsIterator<'a> { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
264 changes: &'a ChangedFiles<'a>, |
46058
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
265 parent: Parent, |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
266 current: u32, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
267 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
268 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
269 impl<'a> Iterator for ActionsIterator<'a> { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
270 type Item = Action<'a>; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
271 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
272 fn next(&mut self) -> Option<Action<'a>> { |
46058
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
273 let copy_flag = match self.parent { |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
274 Parent::FirstParent => P1_COPY, |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
275 Parent::SecondParent => P2_COPY, |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
276 }; |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
277 while self.current < self.changes.nb_items { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
278 let (flags, file, source) = self.changes.entry(self.current); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
279 self.current += 1; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
280 if (flags & ACTION_MASK) == REMOVED { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
281 return Some(Action::Removed(file)); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
282 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
283 let copy = flags & COPY_MASK; |
46058
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
284 if copy == copy_flag { |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
285 return Some(Action::Copied(file, source)); |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
286 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
287 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
288 return None; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
289 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
290 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
291 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
292 /// A small struct whose purpose is to ensure lifetime of bytes referenced in |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
293 /// ChangedFiles |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
294 /// |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
295 /// It is passed to the RevInfoMaker callback who can assign any necessary |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
296 /// content to the `data` attribute. The copy tracing code is responsible for |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
297 /// keeping the DataHolder alive at least as long as the ChangedFiles object. |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
298 pub struct DataHolder<D> { |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
299 /// RevInfoMaker callback should assign data referenced by the |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
300 /// ChangedFiles struct it return to this attribute. The DataHolder |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
301 /// lifetime will be at least as long as the ChangedFiles one. |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
302 pub data: Option<D>, |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
303 } |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
304 |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
305 pub type RevInfoMaker<'a, D> = |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
306 Box<dyn for<'r> Fn(Revision, &'r mut DataHolder<D>) -> RevInfo<'r> + 'a>; |
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
307 |
46058
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
308 /// enum used to carry information about the parent → child currently processed |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
309 #[derive(Copy, Clone, Debug)] |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
310 enum Parent { |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
311 /// The `p1(x) → x` edge |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
312 FirstParent, |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
313 /// The `p2(x) → x` edge |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
314 SecondParent, |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
315 } |
12192fdbf3ac
copies-rust: move the parent token to an enum
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46057
diff
changeset
|
316 |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
317 /// Same as mercurial.copies._combine_changeset_copies, but in Rust. |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
318 /// |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
319 /// Arguments are: |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
320 /// |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
321 /// revs: all revisions to be considered |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
322 /// children: a {parent ? [childrens]} mapping |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
323 /// target_rev: the final revision we are combining copies to |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
324 /// rev_info(rev): callback to get revision information: |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
325 /// * first parent |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
326 /// * second parent |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
327 /// * ChangedFiles |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
328 /// isancestors(low_rev, high_rev): callback to check if a revision is an |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
329 /// ancestor of another |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
330 pub fn combine_changeset_copies<A: Fn(Revision, Revision) -> bool, D>( |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
331 revs: Vec<Revision>, |
46149
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
332 mut children_count: HashMap<Revision, usize>, |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
333 target_rev: Revision, |
46057
e0313b0a6f7e
copies-rust: parse the changed-file sidedata directly in rust
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45975
diff
changeset
|
334 rev_info: RevInfoMaker<D>, |
45972
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
335 is_ancestor: &A, |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
336 ) -> PathCopies { |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
337 let mut all_copies = HashMap::new(); |
45972
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
338 let mut oracle = AncestorOracle::new(is_ancestor); |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
339 |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
340 for rev in revs { |
46149
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
341 let mut d: DataHolder<D> = DataHolder { data: None }; |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
342 let (p1, p2, changes) = rev_info(rev, &mut d); |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
343 |
46149
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
344 // We will chain the copies information accumulated for the parent with |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
345 // the individual copies information the curent revision. Creating a |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
346 // new TimeStampedPath for each `rev` → `children` vertex. |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
347 let mut copies: Option<TimeStampedPathCopies> = None; |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
348 if p1 != NULL_REVISION { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
349 // Retrieve data computed in a previous iteration |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
350 let parent_copies = get_and_clean_parent_copies( |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
351 &mut all_copies, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
352 &mut children_count, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
353 p1, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
354 ); |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
355 if let Some(parent_copies) = parent_copies { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
356 // combine it with data for that revision |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
357 let vertex_copies = add_from_changes( |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
358 &parent_copies, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
359 &changes, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
360 Parent::FirstParent, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
361 rev, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
362 ); |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
363 // keep that data around for potential later combination |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
364 copies = Some(vertex_copies); |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
365 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
366 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
367 if p2 != NULL_REVISION { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
368 // Retrieve data computed in a previous iteration |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
369 let parent_copies = get_and_clean_parent_copies( |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
370 &mut all_copies, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
371 &mut children_count, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
372 p2, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
373 ); |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
374 if let Some(parent_copies) = parent_copies { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
375 // combine it with data for that revision |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
376 let vertex_copies = add_from_changes( |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
377 &parent_copies, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
378 &changes, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
379 Parent::SecondParent, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
380 rev, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
381 ); |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
382 |
46149
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
383 copies = match copies { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
384 None => Some(vertex_copies), |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
385 // Merge has two parents needs to combines their copy |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
386 // information. |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
387 // |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
388 // If we got data from both parents, We need to combine |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
389 // them. |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
390 Some(copies) => Some(merge_copies_dict( |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
391 vertex_copies, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
392 copies, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
393 &changes, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
394 &mut oracle, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
395 )), |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
396 }; |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
397 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
398 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
399 match copies { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
400 Some(copies) => { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
401 all_copies.insert(rev, copies); |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
402 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
403 _ => {} |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
404 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
405 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
406 |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
407 // Drop internal information (like the timestamp) and return the final |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
408 // mapping. |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
409 let tt_result = all_copies |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
410 .remove(&target_rev) |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
411 .expect("target revision was not processed"); |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
412 let mut result = PathCopies::default(); |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
413 for (dest, tt_source) in tt_result { |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
414 if let Some(path) = tt_source.path { |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
415 result.insert(dest, path); |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
416 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
417 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
418 result |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
419 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
420 |
46149
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
421 /// fetch previous computed information |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
422 /// |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
423 /// If no other children are expected to need this information, we drop it from |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
424 /// the cache. |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
425 /// |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
426 /// If parent is not part of the set we are expected to walk, return None. |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
427 fn get_and_clean_parent_copies( |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
428 all_copies: &mut HashMap<Revision, TimeStampedPathCopies>, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
429 children_count: &mut HashMap<Revision, usize>, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
430 parent_rev: Revision, |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
431 ) -> Option<TimeStampedPathCopies> { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
432 let count = children_count.get_mut(&parent_rev)?; |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
433 *count -= 1; |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
434 if *count == 0 { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
435 match all_copies.remove(&parent_rev) { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
436 Some(c) => Some(c), |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
437 None => Some(TimeStampedPathCopies::default()), |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
438 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
439 } else { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
440 match all_copies.get(&parent_rev) { |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
441 Some(c) => Some(c.clone()), |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
442 None => Some(TimeStampedPathCopies::default()), |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
443 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
444 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
445 } |
294d5aca4ff5
copies: iterate over children directly (instead of parents)
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46129
diff
changeset
|
446 |
46059
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
447 /// Combine ChangedFiles with some existing PathCopies information and return |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
448 /// the result |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
449 fn add_from_changes( |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
450 base_copies: &TimeStampedPathCopies, |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
451 changes: &ChangedFiles, |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
452 parent: Parent, |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
453 current_rev: Revision, |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
454 ) -> TimeStampedPathCopies { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
455 let mut copies = base_copies.clone(); |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
456 for action in changes.iter_actions(parent) { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
457 match action { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
458 Action::Copied(dest, source) => { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
459 let entry; |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
460 if let Some(v) = base_copies.get(source) { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
461 entry = match &v.path { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
462 Some(path) => Some((*(path)).to_owned()), |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
463 None => Some(source.to_owned()), |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
464 } |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
465 } else { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
466 entry = Some(source.to_owned()); |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
467 } |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
468 // Each new entry is introduced by the children, we |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
469 // record this information as we will need it to take |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
470 // the right decision when merging conflicting copy |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
471 // information. See merge_copies_dict for details. |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
472 let ttpc = TimeStampedPathCopy { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
473 rev: current_rev, |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
474 path: entry, |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
475 }; |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
476 copies.insert(dest.to_owned(), ttpc); |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
477 } |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
478 Action::Removed(f) => { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
479 // We must drop copy information for removed file. |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
480 // |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
481 // We need to explicitly record them as dropped to |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
482 // propagate this information when merging two |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
483 // TimeStampedPathCopies object. |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
484 if copies.contains_key(f.as_ref()) { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
485 let ttpc = TimeStampedPathCopy { |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
486 rev: current_rev, |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
487 path: None, |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
488 }; |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
489 copies.insert(f.to_owned(), ttpc); |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
490 } |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
491 } |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
492 } |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
493 } |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
494 copies |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
495 } |
dacb771f6dd2
copies-rust: extract the processing of a ChangedFiles in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46058
diff
changeset
|
496 |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
497 /// merge two copies-mapping together, minor and major |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
498 /// |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
499 /// In case of conflict, value from "major" will be picked, unless in some |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
500 /// cases. See inline documentation for details. |
45972
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
501 fn merge_copies_dict<A: Fn(Revision, Revision) -> bool>( |
46128
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
502 mut minor: TimeStampedPathCopies, |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
503 mut major: TimeStampedPathCopies, |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
504 changes: &ChangedFiles, |
45972
8b99c473aae2
copies-rust: move is_ancestor caching within the rust code
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45971
diff
changeset
|
505 oracle: &mut AncestorOracle<A>, |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
506 ) -> TimeStampedPathCopies { |
46127
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
507 // This closure exist as temporary help while multiple developper are |
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
508 // actively working on this code. Feel free to re-inline it once this |
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
509 // code is more settled. |
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
510 let mut cmp_value = |
46129
818502d2f5e3
copies-rust: pre-introduce a PathToken type and use it where applicable
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46128
diff
changeset
|
511 |dest: &PathToken, |
46127
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
512 src_minor: &TimeStampedPathCopy, |
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
513 src_major: &TimeStampedPathCopy| { |
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
514 compare_value(changes, oracle, dest, src_minor, src_major) |
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
515 }; |
45971
cc759d3db1e8
copies-rust: leverage the immutability for efficient update
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45964
diff
changeset
|
516 if minor.is_empty() { |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
517 major |
45971
cc759d3db1e8
copies-rust: leverage the immutability for efficient update
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45964
diff
changeset
|
518 } else if major.is_empty() { |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
519 minor |
46128
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
520 } else if minor.len() * 2 < major.len() { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
521 // Lets says we are merging two TimeStampedPathCopies instance A and B. |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
522 // |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
523 // If A contains N items, the merge result will never contains more |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
524 // than N values differents than the one in A |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
525 // |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
526 // If B contains M items, with M > N, the merge result will always |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
527 // result in a minimum of M - N value differents than the on in |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
528 // A |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
529 // |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
530 // As a result, if N < (M-N), we know that simply iterating over A will |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
531 // yield less difference than iterating over the difference |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
532 // between A and B. |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
533 // |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
534 // This help performance a lot in case were a tiny |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
535 // TimeStampedPathCopies is merged with a much larger one. |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
536 for (dest, src_minor) in minor { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
537 let src_major = major.get(&dest); |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
538 match src_major { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
539 None => major.insert(dest, src_minor), |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
540 Some(src_major) => { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
541 match cmp_value(&dest, &src_minor, src_major) { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
542 MergePick::Any | MergePick::Major => None, |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
543 MergePick::Minor => major.insert(dest, src_minor), |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
544 } |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
545 } |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
546 }; |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
547 } |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
548 major |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
549 } else if major.len() * 2 < minor.len() { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
550 // This use the same rational than the previous block. |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
551 // (Check previous block documentation for details.) |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
552 for (dest, src_major) in major { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
553 let src_minor = minor.get(&dest); |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
554 match src_minor { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
555 None => minor.insert(dest, src_major), |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
556 Some(src_minor) => { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
557 match cmp_value(&dest, src_minor, &src_major) { |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
558 MergePick::Any | MergePick::Minor => None, |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
559 MergePick::Major => minor.insert(dest, src_major), |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
560 } |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
561 } |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
562 }; |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
563 } |
c94d013e2299
copies-rust: add smarter approach for merging small mapping with large mapping
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46127
diff
changeset
|
564 minor |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
565 } else { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
566 let mut override_minor = Vec::new(); |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
567 let mut override_major = Vec::new(); |
45971
cc759d3db1e8
copies-rust: leverage the immutability for efficient update
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45964
diff
changeset
|
568 |
46129
818502d2f5e3
copies-rust: pre-introduce a PathToken type and use it where applicable
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46128
diff
changeset
|
569 let mut to_major = |k: &PathToken, v: &TimeStampedPathCopy| { |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
570 override_major.push((k.clone(), v.clone())) |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
571 }; |
46129
818502d2f5e3
copies-rust: pre-introduce a PathToken type and use it where applicable
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46128
diff
changeset
|
572 let mut to_minor = |k: &PathToken, v: &TimeStampedPathCopy| { |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
573 override_minor.push((k.clone(), v.clone())) |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
574 }; |
45971
cc759d3db1e8
copies-rust: leverage the immutability for efficient update
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45964
diff
changeset
|
575 |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
576 // The diff function leverage detection of the identical subpart if |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
577 // minor and major has some common ancestors. This make it very |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
578 // fast is most case. |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
579 // |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
580 // In case where the two map are vastly different in size, the current |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
581 // approach is still slowish because the iteration will iterate over |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
582 // all the "exclusive" content of the larger on. This situation can be |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
583 // frequent when the subgraph of revision we are processing has a lot |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
584 // of roots. Each roots adding they own fully new map to the mix (and |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
585 // likely a small map, if the path from the root to the "main path" is |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
586 // small. |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
587 // |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
588 // We could do better by detecting such situation and processing them |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
589 // differently. |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
590 for d in minor.diff(&major) { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
591 match d { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
592 DiffItem::Add(k, v) => to_minor(k, v), |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
593 DiffItem::Remove(k, v) => to_major(k, v), |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
594 DiffItem::Update { old, new } => { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
595 let (dest, src_major) = new; |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
596 let (_, src_minor) = old; |
46127
c58c8f1d63b1
copies-rust: hide most of the comparison details inside a closure
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46126
diff
changeset
|
597 match cmp_value(dest, src_minor, src_major) { |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
598 MergePick::Major => to_minor(dest, src_major), |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
599 MergePick::Minor => to_major(dest, src_minor), |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
600 // If the two entry are identical, no need to do |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
601 // anything (but diff should not have yield them) |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
602 MergePick::Any => unreachable!(), |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
603 } |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
604 } |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
605 }; |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
606 } |
45971
cc759d3db1e8
copies-rust: leverage the immutability for efficient update
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
45964
diff
changeset
|
607 |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
608 let updates; |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
609 let mut result; |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
610 if override_major.is_empty() { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
611 result = major |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
612 } else if override_minor.is_empty() { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
613 result = minor |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
614 } else { |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
615 if override_minor.len() < override_major.len() { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
616 updates = override_minor; |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
617 result = minor; |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
618 } else { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
619 updates = override_major; |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
620 result = major; |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
621 } |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
622 for (k, v) in updates { |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
623 result.insert(k, v); |
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
624 } |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
625 } |
46126
94300498491e
copies-rust: move the mapping merging into a else clause
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46125
diff
changeset
|
626 result |
45944
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
627 } |
595979dc924e
copies: introduce a basic Rust function for `combine_changeset_copies`
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff
changeset
|
628 } |
46125
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
629 |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
630 /// represent the side that should prevail when merging two |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
631 /// TimeStampedPathCopies |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
632 enum MergePick { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
633 /// The "major" (p1) side prevails |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
634 Major, |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
635 /// The "minor" (p2) side prevails |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
636 Minor, |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
637 /// Any side could be used (because they are the same) |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
638 Any, |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
639 } |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
640 |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
641 /// decide which side prevails in case of conflicting values |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
642 #[allow(clippy::if_same_then_else)] |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
643 fn compare_value<A: Fn(Revision, Revision) -> bool>( |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
644 changes: &ChangedFiles, |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
645 oracle: &mut AncestorOracle<A>, |
46129
818502d2f5e3
copies-rust: pre-introduce a PathToken type and use it where applicable
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46128
diff
changeset
|
646 dest: &PathToken, |
46125
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
647 src_minor: &TimeStampedPathCopy, |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
648 src_major: &TimeStampedPathCopy, |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
649 ) -> MergePick { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
650 if src_major.path == src_minor.path { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
651 // we have the same value, but from other source; |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
652 if src_major.rev == src_minor.rev { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
653 // If the two entry are identical, they are both valid |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
654 MergePick::Any |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
655 } else if oracle.is_ancestor(src_major.rev, src_minor.rev) { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
656 MergePick::Minor |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
657 } else { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
658 MergePick::Major |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
659 } |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
660 } else if src_major.rev == src_minor.rev { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
661 // We cannot get copy information for both p1 and p2 in the |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
662 // same rev. So this is the same value. |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
663 unreachable!( |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
664 "conflict information from p1 and p2 in the same revision" |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
665 ); |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
666 } else { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
667 let action = changes.get_merge_case(&dest); |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
668 if src_major.path.is_none() && action == MergeCase::Salvaged { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
669 // If the file is "deleted" in the major side but was |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
670 // salvaged by the merge, we keep the minor side alive |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
671 MergePick::Minor |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
672 } else if src_minor.path.is_none() && action == MergeCase::Salvaged { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
673 // If the file is "deleted" in the minor side but was |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
674 // salvaged by the merge, unconditionnaly preserve the |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
675 // major side. |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
676 MergePick::Major |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
677 } else if action == MergeCase::Merged { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
678 // If the file was actively merged, copy information |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
679 // from each side might conflict. The major side will |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
680 // win such conflict. |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
681 MergePick::Major |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
682 } else if oracle.is_ancestor(src_major.rev, src_minor.rev) { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
683 // If the minor side is strictly newer than the major |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
684 // side, it should be kept. |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
685 MergePick::Minor |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
686 } else if src_major.path.is_some() { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
687 // without any special case, the "major" value win |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
688 // other the "minor" one. |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
689 MergePick::Major |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
690 } else if oracle.is_ancestor(src_minor.rev, src_major.rev) { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
691 // the "major" rev is a direct ancestors of "minor", |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
692 // any different value should |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
693 // overwrite |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
694 MergePick::Major |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
695 } else { |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
696 // major version is None (so the file was deleted on |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
697 // that branch) and that branch is independant (neither |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
698 // minor nor major is an ancestors of the other one.) |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
699 // We preserve the new |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
700 // information about the new file. |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
701 MergePick::Minor |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
702 } |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
703 } |
61afe6215aef
copies-rust: extract conflicting value comparison in its own function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
46059
diff
changeset
|
704 } |