Mercurial > public > mercurial-scm > hg-stable
annotate rust/hg-core/src/dirstate_tree/owning.rs @ 52078:ea0467ed76aa
rust-dirstate-map: use a more precise identity
This is closer to the behavior of what Python does. So far, we were checking
only the inode, but this might not be good enough for the v1 case.
author | Rapha?l Gom?s <rgomes@octobus.net> |
---|---|
date | Thu, 03 Oct 2024 16:35:31 +0200 |
parents | 88aa21d654e5 |
children |
rev | line source |
---|---|
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
1 use crate::{DirstateError, DirstateParents}; |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
2 |
52078
ea0467ed76aa
rust-dirstate-map: use a more precise identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
52057
diff
changeset
|
3 use super::dirstate_map::{DirstateIdentity, DirstateMap}; |
50690
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
4 use self_cell::self_cell; |
47982
4afd6cc447b9
rust: Make OwningDirstateMap generic and move it into hg-core
Simon Sapin <simon.sapin@octobus.net>
parents:
47682
diff
changeset
|
5 use std::ops::Deref; |
47137
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
6 |
50690
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
7 self_cell!( |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
8 /// Keep a `DirstateMap<'owner>` next to the `owner` buffer that it |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
9 /// borrows. |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
10 pub struct OwningDirstateMap { |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
11 owner: Box<dyn Deref<Target = [u8]> + Send>, |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
12 #[covariant] |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
13 dependent: DirstateMap, |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
14 } |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
15 ); |
47137
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
16 |
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
17 impl OwningDirstateMap { |
52078
ea0467ed76aa
rust-dirstate-map: use a more precise identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
52057
diff
changeset
|
18 pub fn new_empty<OnDisk>( |
ea0467ed76aa
rust-dirstate-map: use a more precise identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
52057
diff
changeset
|
19 on_disk: OnDisk, |
ea0467ed76aa
rust-dirstate-map: use a more precise identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
52057
diff
changeset
|
20 identity: Option<DirstateIdentity>, |
ea0467ed76aa
rust-dirstate-map: use a more precise identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
52057
diff
changeset
|
21 ) -> Self |
47982
4afd6cc447b9
rust: Make OwningDirstateMap generic and move it into hg-core
Simon Sapin <simon.sapin@octobus.net>
parents:
47682
diff
changeset
|
22 where |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
23 OnDisk: Deref<Target = [u8]> + Send + 'static, |
47982
4afd6cc447b9
rust: Make OwningDirstateMap generic and move it into hg-core
Simon Sapin <simon.sapin@octobus.net>
parents:
47682
diff
changeset
|
24 { |
4afd6cc447b9
rust: Make OwningDirstateMap generic and move it into hg-core
Simon Sapin <simon.sapin@octobus.net>
parents:
47682
diff
changeset
|
25 let on_disk = Box::new(on_disk); |
47137
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
26 |
52057
88aa21d654e5
rust-dirstate: actually remember the identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50690
diff
changeset
|
27 OwningDirstateMap::new(on_disk, |bytes| { |
88aa21d654e5
rust-dirstate: actually remember the identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50690
diff
changeset
|
28 let mut empty = DirstateMap::empty(bytes); |
88aa21d654e5
rust-dirstate: actually remember the identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50690
diff
changeset
|
29 empty.identity = identity; |
88aa21d654e5
rust-dirstate: actually remember the identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50690
diff
changeset
|
30 empty |
88aa21d654e5
rust-dirstate: actually remember the identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50690
diff
changeset
|
31 }) |
47137
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
32 } |
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
33 |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
34 pub fn new_v1<OnDisk>( |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
35 on_disk: OnDisk, |
52078
ea0467ed76aa
rust-dirstate-map: use a more precise identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
52057
diff
changeset
|
36 identity: Option<DirstateIdentity>, |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
37 ) -> Result<(Self, DirstateParents), DirstateError> |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
38 where |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
39 OnDisk: Deref<Target = [u8]> + Send + 'static, |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
40 { |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
41 let on_disk = Box::new(on_disk); |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
42 let mut parents = DirstateParents::NULL; |
47982
4afd6cc447b9
rust: Make OwningDirstateMap generic and move it into hg-core
Simon Sapin <simon.sapin@octobus.net>
parents:
47682
diff
changeset
|
43 |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
44 Ok(( |
50690
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
45 OwningDirstateMap::try_new(on_disk, |bytes| { |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
46 DirstateMap::new_v1(bytes, identity).map(|(dmap, p)| { |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
47 parents = p.unwrap_or(DirstateParents::NULL); |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
48 dmap |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
49 }) |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
50 })?, |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
51 parents, |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
52 )) |
47137
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
53 } |
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
54 |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
55 pub fn new_v2<OnDisk>( |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
56 on_disk: OnDisk, |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
57 data_size: usize, |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
58 metadata: &[u8], |
49701
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
59 uuid: Vec<u8>, |
52078
ea0467ed76aa
rust-dirstate-map: use a more precise identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
52057
diff
changeset
|
60 identity: Option<DirstateIdentity>, |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
61 ) -> Result<Self, DirstateError> |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
62 where |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
63 OnDisk: Deref<Target = [u8]> + Send + 'static, |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
64 { |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
65 let on_disk = Box::new(on_disk); |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
66 |
50690
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
67 OwningDirstateMap::try_new(on_disk, |bytes| { |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
68 DirstateMap::new_v2(bytes, data_size, metadata, uuid, identity) |
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
69 }) |
47137
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
70 } |
47982
4afd6cc447b9
rust: Make OwningDirstateMap generic and move it into hg-core
Simon Sapin <simon.sapin@octobus.net>
parents:
47682
diff
changeset
|
71 |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
72 pub fn with_dmap_mut<R>( |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
73 &mut self, |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
74 f: impl FnOnce(&mut DirstateMap) -> R, |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
75 ) -> R { |
50690
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
76 self.with_dependent_mut(|_owner, dmap| f(dmap)) |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
77 } |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
78 |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
79 pub fn get_map(&self) -> &DirstateMap { |
50690
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
80 self.borrow_dependent() |
48825
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
81 } |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
82 |
dd6b67d5c256
rust: fix unsound `OwningDirstateMap`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48824
diff
changeset
|
83 pub fn on_disk(&self) -> &[u8] { |
50690
2cc5de261d76
rust-hg-core: move from `ouroboros` to `self_cell`
Rapha?l Gom?s <rgomes@octobus.net>
parents:
50252
diff
changeset
|
84 self.borrow_owner() |
47982
4afd6cc447b9
rust: Make OwningDirstateMap generic and move it into hg-core
Simon Sapin <simon.sapin@octobus.net>
parents:
47682
diff
changeset
|
85 } |
49701
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
86 |
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
87 pub fn old_uuid(&self) -> Option<&[u8]> { |
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
88 self.get_map().old_uuid.as_deref() |
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
89 } |
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
90 |
52078
ea0467ed76aa
rust-dirstate-map: use a more precise identity
Rapha?l Gom?s <rgomes@octobus.net>
parents:
52057
diff
changeset
|
91 pub fn old_identity(&self) -> Option<DirstateIdentity> { |
49703
dbe09fb038fc
rhg: remember the inode of .hg/dirstate
Rapha?l Gom?s <rgomes@octobus.net>
parents:
49701
diff
changeset
|
92 self.get_map().identity |
dbe09fb038fc
rhg: remember the inode of .hg/dirstate
Rapha?l Gom?s <rgomes@octobus.net>
parents:
49701
diff
changeset
|
93 } |
dbe09fb038fc
rhg: remember the inode of .hg/dirstate
Rapha?l Gom?s <rgomes@octobus.net>
parents:
49701
diff
changeset
|
94 |
49701
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
95 pub fn old_data_size(&self) -> usize { |
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
96 self.get_map().old_data_size |
6cce0afc1454
rust-dirstate: remember the data file uuid dirstate was loaded with
Rapha?l Gom?s <rgomes@octobus.net>
parents:
48825
diff
changeset
|
97 } |
47137
d8ac62374943
dirstate-tree: Make `DirstateMap` borrow from a bytes buffer
Simon Sapin <simon.sapin@octobus.net>
parents:
diff
changeset
|
98 } |