##// END OF EJS Templates
rhg: fix dirstate-v2 data file removal system...
rhg: fix dirstate-v2 data file removal system In D12581 I introduced logic to remove the previous dirstate-v2 data file after a new one is created (and its corresponding docket), but the logic was flawed. I fixed it and made it simpler to understand by gather all logic in a single expression. Differential Revision: https://phab.mercurial-scm.org/D12586

File last commit:

r49991:38e5bb14 default
r50044:f2ef6a4f stable
Show More
item.rs
285 lines | 7.8 KiB | application/rls-services+xml | RustLexer
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 use cpython::exc;
dirstate: add a concept of "fallback" flags to dirstate item...
r49068 use cpython::ObjectProtocol;
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 use cpython::PyBytes;
use cpython::PyErr;
use cpython::PyNone;
use cpython::PyObject;
use cpython::PyResult;
use cpython::Python;
use cpython::PythonObject;
use hg::dirstate::DirstateEntry;
use hg::dirstate::EntryState;
Simon Sapin
dirstate: store mtimes with nanosecond precision in memory...
r49079 use hg::dirstate::TruncatedTimestamp;
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 use std::cell::Cell;
use std::convert::TryFrom;
py_class!(pub class DirstateItem |py| {
data entry: Cell<DirstateEntry>;
def __new__(
_cls,
wc_tracked: bool = false,
p1_tracked: bool = false,
dirstate-item: change the internal storage and constructor value...
r48950 p2_info: bool = false,
has_meaningful_data: bool = true,
has_meaningful_mtime: bool = true,
dirstate-item: add a "second_ambiguous` flag in the mtime tuple...
r49227 parentfiledata: Option<(u32, u32, Option<(u32, u32, bool)>)> = None,
dirstate: make DirstateItem constructor accept fallback value...
r49069 fallback_exec: Option<bool> = None,
fallback_symlink: Option<bool> = None,
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857
) -> PyResult<DirstateItem> {
dirstate-item: change the internal storage and constructor value...
r48950 let mut mode_size_opt = None;
let mut mtime_opt = None;
if let Some((mode, size, mtime)) = parentfiledata {
if has_meaningful_data {
mode_size_opt = Some((mode, size))
}
if has_meaningful_mtime {
dirstate-item: allow mtime to be None in "parentdata"...
r49201 if let Some(m) = mtime {
mtime_opt = Some(timestamp(py, m)?);
}
dirstate-item: change the internal storage and constructor value...
r48950 }
}
Simon Sapin
dirstate-v2: Store a bitfield on disk instead of v1-like state...
r48951 let entry = DirstateEntry::from_v2_data(
dirstate: make DirstateItem constructor accept fallback value...
r49069 wc_tracked,
p1_tracked,
p2_info,
mode_size_opt,
mtime_opt,
fallback_exec,
fallback_symlink,
dirstate-item: change the internal storage and constructor value...
r48950 );
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 DirstateItem::create_instance(py, Cell::new(entry))
}
@property
def state(&self) -> PyResult<PyBytes> {
let state_byte: u8 = self.entry(py).get().state().into();
Ok(PyBytes::new(py, &[state_byte]))
}
@property
def mode(&self) -> PyResult<i32> {
Ok(self.entry(py).get().mode())
}
@property
def size(&self) -> PyResult<i32> {
Ok(self.entry(py).get().size())
}
@property
def mtime(&self) -> PyResult<i32> {
Ok(self.entry(py).get().mtime())
}
@property
dirstate: add a concept of "fallback" flags to dirstate item...
r49068 def has_fallback_exec(&self) -> PyResult<bool> {
match self.entry(py).get().get_fallback_exec() {
Some(_) => Ok(true),
None => Ok(false),
}
}
@property
def fallback_exec(&self) -> PyResult<Option<bool>> {
match self.entry(py).get().get_fallback_exec() {
Some(exec) => Ok(Some(exec)),
None => Ok(None),
}
}
@fallback_exec.setter
def set_fallback_exec(&self, value: Option<PyObject>) -> PyResult<()> {
match value {
None => {self.entry(py).get().set_fallback_exec(None);},
Some(value) => {
if value.is_none(py) {
self.entry(py).get().set_fallback_exec(None);
} else {
self.entry(py).get().set_fallback_exec(
Some(value.is_true(py)?)
);
}},
}
Ok(())
}
@property
def has_fallback_symlink(&self) -> PyResult<bool> {
match self.entry(py).get().get_fallback_symlink() {
Some(_) => Ok(true),
None => Ok(false),
}
}
@property
def fallback_symlink(&self) -> PyResult<Option<bool>> {
match self.entry(py).get().get_fallback_symlink() {
Some(symlink) => Ok(Some(symlink)),
None => Ok(None),
}
}
@fallback_symlink.setter
def set_fallback_symlink(&self, value: Option<PyObject>) -> PyResult<()> {
match value {
None => {self.entry(py).get().set_fallback_symlink(None);},
Some(value) => {
if value.is_none(py) {
self.entry(py).get().set_fallback_symlink(None);
} else {
self.entry(py).get().set_fallback_symlink(
Some(value.is_true(py)?)
);
}},
}
Ok(())
}
@property
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 def tracked(&self) -> PyResult<bool> {
Ok(self.entry(py).get().tracked())
}
@property
dirstate-item: introduce a `p1_tracked` property...
r48955 def p1_tracked(&self) -> PyResult<bool> {
Ok(self.entry(py).get().p1_tracked())
}
@property
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 def added(&self) -> PyResult<bool> {
Ok(self.entry(py).get().added())
}
dirstate-item: introduce a `p2_info` property that combine two others...
r48954
@property
def p2_info(&self) -> PyResult<bool> {
Ok(self.entry(py).get().p2_info())
}
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 @property
def removed(&self) -> PyResult<bool> {
Ok(self.entry(py).get().removed())
}
@property
dirstate-item: introduce a `maybe_clean` property...
r48898 def maybe_clean(&self) -> PyResult<bool> {
Ok(self.entry(py).get().maybe_clean())
}
dirstate-item: introduce a `any_tracked` property...
r48899 @property
def any_tracked(&self) -> PyResult<bool> {
Ok(self.entry(py).get().any_tracked())
}
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 def v1_state(&self) -> PyResult<PyBytes> {
let (state, _mode, _size, _mtime) = self.entry(py).get().v1_data();
let state_byte: u8 = state.into();
Ok(PyBytes::new(py, &[state_byte]))
}
def v1_mode(&self) -> PyResult<i32> {
let (_state, mode, _size, _mtime) = self.entry(py).get().v1_data();
Ok(mode)
}
def v1_size(&self) -> PyResult<i32> {
let (_state, _mode, size, _mtime) = self.entry(py).get().v1_data();
Ok(size)
}
def v1_mtime(&self) -> PyResult<i32> {
let (_state, _mode, _size, mtime) = self.entry(py).get().v1_data();
Ok(mtime)
}
dirstate-item: add a "second_ambiguous` flag in the mtime tuple...
r49227 def mtime_likely_equal_to(&self, other: (u32, u32, bool))
-> PyResult<bool> {
Simon Sapin
dirstate: store mtimes with nanosecond precision in memory...
r49079 if let Some(mtime) = self.entry(py).get().truncated_mtime() {
Ok(mtime.likely_equal(timestamp(py, other)?))
} else {
Ok(false)
}
}
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 @classmethod
def from_v1_data(
_cls,
state: PyBytes,
mode: i32,
size: i32,
mtime: i32,
) -> PyResult<Self> {
let state = <[u8; 1]>::try_from(state.data(py))
.ok()
.and_then(|state| EntryState::try_from(state[0]).ok())
.ok_or_else(|| PyErr::new::<exc::ValueError, _>(py, "invalid state"))?;
let entry = DirstateEntry::from_v1_data(state, mode, size, mtime);
DirstateItem::create_instance(py, Cell::new(entry))
}
dirstate-item: implement `drop_merge_data` on the Rust DirstateItem...
r48946 def drop_merge_data(&self) -> PyResult<PyNone> {
self.update(py, |entry| entry.drop_merge_data());
Ok(PyNone)
}
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 def set_clean(
&self,
Simon Sapin
dirstate-v2: Store unsigned integers inside DirstateEntry...
r49008 mode: u32,
size: u32,
dirstate-item: add a "second_ambiguous` flag in the mtime tuple...
r49227 mtime: (u32, u32, bool),
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 ) -> PyResult<PyNone> {
Simon Sapin
dirstate: store mtimes with nanosecond precision in memory...
r49079 let mtime = timestamp(py, mtime)?;
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 self.update(py, |entry| entry.set_clean(mode, size, mtime));
Ok(PyNone)
}
def set_possibly_dirty(&self) -> PyResult<PyNone> {
self.update(py, |entry| entry.set_possibly_dirty());
Ok(PyNone)
}
def set_tracked(&self) -> PyResult<PyNone> {
self.update(py, |entry| entry.set_tracked());
Ok(PyNone)
}
def set_untracked(&self) -> PyResult<PyNone> {
self.update(py, |entry| entry.set_untracked());
Ok(PyNone)
}
});
impl DirstateItem {
pub fn new_as_pyobject(
py: Python<'_>,
entry: DirstateEntry,
) -> PyResult<PyObject> {
Ok(DirstateItem::create_instance(py, Cell::new(entry))?.into_object())
}
Simon Sapin
dirstate: Skip no-op conversion in Rust DirstateMap::set_v1...
r48859 pub fn get_entry(&self, py: Python<'_>) -> DirstateEntry {
self.entry(py).get()
}
Simon Sapin
rust: Add Python bindings for DirstateEntry as rustext.dirstate.DirstateItem...
r48857 // TODO: Use https://doc.rust-lang.org/std/cell/struct.Cell.html#method.update instead when it’s stable
pub fn update(&self, py: Python<'_>, f: impl FnOnce(&mut DirstateEntry)) {
let mut entry = self.entry(py).get();
f(&mut entry);
self.entry(py).set(entry)
}
}
Simon Sapin
dirstate: store mtimes with nanosecond precision in memory...
r49079
pub(crate) fn timestamp(
py: Python<'_>,
dirstate-item: add a "second_ambiguous` flag in the mtime tuple...
r49227 (s, ns, second_ambiguous): (u32, u32, bool),
Simon Sapin
dirstate: store mtimes with nanosecond precision in memory...
r49079 ) -> PyResult<TruncatedTimestamp> {
dirstate-item: add a "second_ambiguous` flag in the mtime tuple...
r49227 TruncatedTimestamp::from_already_truncated(s, ns, second_ambiguous)
.map_err(|_| {
PyErr::new::<exc::ValueError, _>(
py,
"expected mtime truncated to 31 bits",
)
})
Simon Sapin
dirstate: store mtimes with nanosecond precision in memory...
r49079 }