rust-dirstatemap: add `set_clean` method
This is the new dirstate API that has already been moved to in Python.
Differential Revision: https://phab.mercurial-scm.org/D12502
--- a/rust/hg-core/src/dirstate_tree/dirstate_map.rs Wed Mar 23 17:13:18 2022 +0100
+++ b/rust/hg-core/src/dirstate_tree/dirstate_map.rs Mon Mar 28 18:02:50 2022 +0200
@@ -21,6 +21,7 @@
use crate::utils::hg_path::{HgPath, HgPathBuf};
use crate::DirstateEntry;
use crate::DirstateError;
+use crate::DirstateMapError;
use crate::DirstateParents;
use crate::DirstateStatus;
use crate::EntryState;
@@ -764,6 +765,32 @@
Ok(())
}
+ fn set_clean(
+ &mut self,
+ filename: &HgPath,
+ old_entry: DirstateEntry,
+ mode: u32,
+ size: u32,
+ mtime: TruncatedTimestamp,
+ ) -> Result<(), DirstateError> {
+ let node = Self::get_or_insert_node(
+ self.on_disk,
+ &mut self.unreachable_bytes,
+ &mut self.root,
+ filename,
+ WithBasename::to_cow_owned,
+ |ancestor| {
+ if !old_entry.tracked() {
+ ancestor.tracked_descendants_count += 1;
+ }
+ },
+ )?;
+ let mut new_entry = old_entry.clone();
+ new_entry.set_clean(mode, size, mtime);
+ node.data = NodeData::Entry(new_entry);
+ Ok(())
+ }
+
fn iter_nodes<'tree>(
&'tree self,
) -> impl Iterator<
@@ -881,6 +908,27 @@
self.with_dmap_mut(|map| map.set_tracked(filename, old_entry_opt))
}
+ pub fn set_clean(
+ &mut self,
+ filename: &HgPath,
+ mode: u32,
+ size: u32,
+ mtime: TruncatedTimestamp,
+ ) -> Result<(), DirstateError> {
+ let old_entry = match self.get(filename)? {
+ None => {
+ return Err(
+ DirstateMapError::PathNotFound(filename.into()).into()
+ )
+ }
+ Some(e) => e,
+ };
+ self.copy_map_remove(filename)?;
+ self.with_dmap_mut(|map| {
+ map.set_clean(filename, old_entry, mode, size, mtime)
+ })
+ }
+
pub fn reset_state(
&mut self,
filename: &HgPath,
--- a/rust/hg-cpython/src/dirstate/dirstate_map.rs Wed Mar 23 17:13:18 2022 +0100
+++ b/rust/hg-cpython/src/dirstate/dirstate_map.rs Mon Mar 28 18:02:50 2022 +0200
@@ -142,6 +142,28 @@
Ok(was_tracked.to_py_object(py))
}
+ def set_clean(
+ &self,
+ f: PyObject,
+ mode: u32,
+ size: u32,
+ mtime: (i64, u32, bool)
+ ) -> PyResult<PyNone> {
+ let (mtime_s, mtime_ns, second_ambiguous) = mtime;
+ let timestamp = TruncatedTimestamp::new_truncate(
+ mtime_s, mtime_ns, second_ambiguous
+ );
+ let bytes = f.extract::<PyBytes>(py)?;
+ let path = HgPath::new(bytes.data(py));
+ let res = self.inner(py).borrow_mut().set_clean(
+ path, mode, size, timestamp,
+ );
+ res.or_else(|_| {
+ Err(PyErr::new::<exc::OSError, _>(py, "Dirstate error".to_string()))
+ })?;
+ Ok(PyNone)
+ }
+
def reset_state(
&self,
f: PyObject,