Skip to main content

honeycomb_core/cmap/dim2/links/
mod.rs

1mod one;
2mod two;
3
4use fast_stm::atomically_with_err;
5
6use crate::cmap::{CMap2, DartIdType, LinkError};
7use crate::geometry::CoordsFloat;
8use crate::stm::{Transaction, TransactionClosureResult};
9
10/// # **Link operations**
11impl<T: CoordsFloat> CMap2<T> {
12    /// `I`-link operator.
13    ///
14    /// # Description
15    ///
16    /// This operation corresponds to coherently linking two darts via their *β* images. Unlike
17    /// sewing, this does not alter associated attributes. For a thorough explanation of this
18    /// operation, its hypothesis & consequences, refer to the [user guide][UG].
19    ///
20    /// [UG]: https://lihpc-computational-geometry.github.io/honeycomb/user-guide/definitions/sew.html
21    ///
22    /// # Arguments
23    ///
24    /// - `const I: u8` -- Link dimension.
25    /// - `t: &mut Transaction` -- Transaction associated to the operation.
26    /// - `ld: DartIdType` -- First dart ID.
27    /// - `rd: DartIdType` -- Second dart ID.
28    ///
29    /// # Errors
30    ///
31    /// This method should be called in a transactional context. The `Result` is then used to
32    /// validate the transaction; Errors should not be processed manually, only processed via the
33    /// `?` operator. The policy in case of failure can be defined when creating the transaction,
34    /// using `Transaction::with_control`.
35    ///
36    /// It may return an error if the transaction fails or if the link fails; See [`LinkError`] for
37    /// more detail about the latter.
38    ///
39    /// # Panics
40    ///
41    /// The method may panic if:
42    /// - `I >= 3` or `I == 0`,
43    /// - the two darts are not `I`-linkable.
44    pub fn link_tx<const I: u8>(
45        &self,
46        t: &mut Transaction,
47        ld: DartIdType,
48        rd: DartIdType,
49    ) -> TransactionClosureResult<(), LinkError> {
50        // these assertions + match on a const are optimized away
51        assert!(I < 3);
52        assert_ne!(I, 0);
53        match I {
54            1 => self.one_link_tx(t, ld, rd),
55            2 => self.two_link_tx(t, ld, rd),
56            _ => unreachable!(),
57        }
58    }
59
60    #[allow(clippy::missing_errors_doc)]
61    /// `I`-unlink operator.
62    ///
63    /// # Description
64    ///
65    /// This operation corresponds to unlinking two darts by resetting their *β* images. Unlike
66    /// unsewing, this does not alter associated attributes. For a thorough explanation of this
67    /// operation, its hypothesis & consequences, refer to the [user guide][UG].
68    ///
69    /// [UG]: https://lihpc-computational-geometry.github.io/honeycomb/user-guide/definitions/sew.html
70    ///
71    /// # Arguments
72    ///
73    /// - `const I: u8` -- Unlink dimension.
74    /// - `t: &mut Transaction` -- Transaction associated to the operation.
75    /// - `ld: DartIdType` -- First dart ID.
76    ///
77    /// The second dart ID is fetched using `I` and `ld`.
78    ///
79    /// # Return / Errors
80    ///
81    /// This method returns the old value of *β<sub>I</sub>(ld)*.
82    ///
83    /// This method should be called in a transactional context. The `Result` is then used to
84    /// validate the transaction; Errors should not be processed manually, only processed via the
85    /// `?` operator. The policy in case of failure can be defined when creating the transaction,
86    /// using `Transaction::with_control`.
87    ///
88    /// It may return an error if the transaction fails or if the link fails; See [`LinkError`] for
89    /// more detail about the latter.
90    ///
91    /// # Panics
92    ///
93    /// The method may panic if:
94    /// - `I >= 3` or `I == 0`,
95    /// - `ld` is already `I`-free.
96    pub fn unlink_tx<const I: u8>(
97        &self,
98        t: &mut Transaction,
99        ld: DartIdType,
100    ) -> TransactionClosureResult<DartIdType, LinkError> {
101        // these assertions + match on a const are optimized away
102        assert!(I < 3);
103        assert_ne!(I, 0);
104        match I {
105            1 => self.one_unlink_tx(t, ld),
106            2 => self.two_unlink_tx(t, ld),
107            _ => unreachable!(),
108        }
109    }
110
111    #[allow(clippy::missing_errors_doc, clippy::missing_panics_doc)]
112    /// `I`-link operator.
113    ///
114    /// This variant is equivalent to [`link`][Self::link], but internally uses a transaction that
115    /// will be retried until validated.
116    pub fn link<const I: u8>(&self, ld: DartIdType, rd: DartIdType) -> Result<(), LinkError> {
117        // these assertions + match on a const are optimized away
118        assert!(I < 3);
119        assert_ne!(I, 0);
120        match I {
121            1 => atomically_with_err(|t| self.one_link_tx(t, ld, rd)),
122            2 => atomically_with_err(|t| self.two_link_tx(t, ld, rd)),
123            _ => unreachable!(),
124        }
125    }
126
127    #[allow(clippy::missing_errors_doc, clippy::missing_panics_doc)]
128    /// # `I`-unlink operator.
129    ///
130    /// This variant is equivalent to [`unlink`][Self::unlink], but internally uses a transaction
131    /// that will be retried until validated.
132    pub fn unlink<const I: u8>(&self, ld: DartIdType) -> Result<DartIdType, LinkError> {
133        // these assertions + match on a const are optimized away
134        assert!(I < 3);
135        assert_ne!(I, 0);
136        match I {
137            1 => atomically_with_err(|t| self.one_unlink_tx(t, ld)),
138            2 => atomically_with_err(|t| self.two_unlink_tx(t, ld)),
139            _ => unreachable!(),
140        }
141    }
142}