##// END OF EJS Templates
rust: remove an unused error variant DirstateMapError::EmptyPath
Arseniy Alekseyev -
r51428:a8531bd9 default
parent child Browse files
Show More
@@ -1,136 +1,132 b''
1 // Copyright 2018-2020 Georges Racinet <georges.racinet@octobus.net>
1 // Copyright 2018-2020 Georges Racinet <georges.racinet@octobus.net>
2 // and Mercurial contributors
2 // and Mercurial contributors
3 //
3 //
4 // This software may be used and distributed according to the terms of the
4 // This software may be used and distributed according to the terms of the
5 // GNU General Public License version 2 or any later version.
5 // GNU General Public License version 2 or any later version.
6
6
7 mod ancestors;
7 mod ancestors;
8 pub mod dagops;
8 pub mod dagops;
9 pub mod errors;
9 pub mod errors;
10 pub mod narrow;
10 pub mod narrow;
11 pub mod sparse;
11 pub mod sparse;
12 pub use ancestors::{AncestorsIterator, MissingAncestors};
12 pub use ancestors::{AncestorsIterator, MissingAncestors};
13 pub mod dirstate;
13 pub mod dirstate;
14 pub mod dirstate_tree;
14 pub mod dirstate_tree;
15 pub mod discovery;
15 pub mod discovery;
16 pub mod exit_codes;
16 pub mod exit_codes;
17 pub mod requirements;
17 pub mod requirements;
18 pub mod testing; // unconditionally built, for use from integration tests
18 pub mod testing; // unconditionally built, for use from integration tests
19 pub use dirstate::{
19 pub use dirstate::{
20 dirs_multiset::{DirsMultiset, DirsMultisetIter},
20 dirs_multiset::{DirsMultiset, DirsMultisetIter},
21 status::{
21 status::{
22 BadMatch, BadType, DirstateStatus, HgPathCow, StatusError,
22 BadMatch, BadType, DirstateStatus, HgPathCow, StatusError,
23 StatusOptions,
23 StatusOptions,
24 },
24 },
25 DirstateEntry, DirstateParents, EntryState,
25 DirstateEntry, DirstateParents, EntryState,
26 };
26 };
27 pub mod copy_tracing;
27 pub mod copy_tracing;
28 mod filepatterns;
28 mod filepatterns;
29 pub mod matchers;
29 pub mod matchers;
30 pub mod repo;
30 pub mod repo;
31 pub mod revlog;
31 pub mod revlog;
32 pub use revlog::*;
32 pub use revlog::*;
33 pub mod checkexec;
33 pub mod checkexec;
34 pub mod config;
34 pub mod config;
35 pub mod lock;
35 pub mod lock;
36 pub mod logging;
36 pub mod logging;
37 pub mod operations;
37 pub mod operations;
38 pub mod revset;
38 pub mod revset;
39 pub mod utils;
39 pub mod utils;
40 pub mod vfs;
40 pub mod vfs;
41
41
42 use crate::utils::hg_path::{HgPathBuf, HgPathError};
42 use crate::utils::hg_path::{HgPathBuf, HgPathError};
43 pub use filepatterns::{
43 pub use filepatterns::{
44 parse_pattern_syntax, read_pattern_file, IgnorePattern,
44 parse_pattern_syntax, read_pattern_file, IgnorePattern,
45 PatternFileWarning, PatternSyntax,
45 PatternFileWarning, PatternSyntax,
46 };
46 };
47 use std::collections::HashMap;
47 use std::collections::HashMap;
48 use std::fmt;
48 use std::fmt;
49 use twox_hash::RandomXxHashBuilder64;
49 use twox_hash::RandomXxHashBuilder64;
50
50
51 pub type LineNumber = usize;
51 pub type LineNumber = usize;
52
52
53 /// Rust's default hasher is too slow because it tries to prevent collision
53 /// Rust's default hasher is too slow because it tries to prevent collision
54 /// attacks. We are not concerned about those: if an ill-minded person has
54 /// attacks. We are not concerned about those: if an ill-minded person has
55 /// write access to your repository, you have other issues.
55 /// write access to your repository, you have other issues.
56 pub type FastHashMap<K, V> = HashMap<K, V, RandomXxHashBuilder64>;
56 pub type FastHashMap<K, V> = HashMap<K, V, RandomXxHashBuilder64>;
57
57
58 // TODO: should this be the default `FastHashMap` for all of hg-core, not just
58 // TODO: should this be the default `FastHashMap` for all of hg-core, not just
59 // dirstate_tree? How does XxHash compare with AHash, hashbrown’s default?
59 // dirstate_tree? How does XxHash compare with AHash, hashbrown’s default?
60 pub type FastHashbrownMap<K, V> =
60 pub type FastHashbrownMap<K, V> =
61 hashbrown::HashMap<K, V, RandomXxHashBuilder64>;
61 hashbrown::HashMap<K, V, RandomXxHashBuilder64>;
62
62
63 #[derive(Debug, PartialEq)]
63 #[derive(Debug, PartialEq)]
64 pub enum DirstateMapError {
64 pub enum DirstateMapError {
65 PathNotFound(HgPathBuf),
65 PathNotFound(HgPathBuf),
66 EmptyPath,
67 InvalidPath(HgPathError),
66 InvalidPath(HgPathError),
68 }
67 }
69
68
70 impl fmt::Display for DirstateMapError {
69 impl fmt::Display for DirstateMapError {
71 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
70 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
72 match self {
71 match self {
73 DirstateMapError::PathNotFound(_) => {
72 DirstateMapError::PathNotFound(_) => {
74 f.write_str("expected a value, found none")
73 f.write_str("expected a value, found none")
75 }
74 }
76 DirstateMapError::EmptyPath => {
77 f.write_str("Overflow in dirstate.")
78 }
79 DirstateMapError::InvalidPath(path_error) => path_error.fmt(f),
75 DirstateMapError::InvalidPath(path_error) => path_error.fmt(f),
80 }
76 }
81 }
77 }
82 }
78 }
83
79
84 #[derive(Debug, derive_more::From)]
80 #[derive(Debug, derive_more::From)]
85 pub enum DirstateError {
81 pub enum DirstateError {
86 Map(DirstateMapError),
82 Map(DirstateMapError),
87 Common(errors::HgError),
83 Common(errors::HgError),
88 }
84 }
89
85
90 impl fmt::Display for DirstateError {
86 impl fmt::Display for DirstateError {
91 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
87 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
92 match self {
88 match self {
93 DirstateError::Map(error) => error.fmt(f),
89 DirstateError::Map(error) => error.fmt(f),
94 DirstateError::Common(error) => error.fmt(f),
90 DirstateError::Common(error) => error.fmt(f),
95 }
91 }
96 }
92 }
97 }
93 }
98
94
99 #[derive(Debug, derive_more::From)]
95 #[derive(Debug, derive_more::From)]
100 pub enum PatternError {
96 pub enum PatternError {
101 #[from]
97 #[from]
102 Path(HgPathError),
98 Path(HgPathError),
103 UnsupportedSyntax(String),
99 UnsupportedSyntax(String),
104 UnsupportedSyntaxInFile(String, String, usize),
100 UnsupportedSyntaxInFile(String, String, usize),
105 TooLong(usize),
101 TooLong(usize),
106 #[from]
102 #[from]
107 IO(std::io::Error),
103 IO(std::io::Error),
108 /// Needed a pattern that can be turned into a regex but got one that
104 /// Needed a pattern that can be turned into a regex but got one that
109 /// can't. This should only happen through programmer error.
105 /// can't. This should only happen through programmer error.
110 NonRegexPattern(IgnorePattern),
106 NonRegexPattern(IgnorePattern),
111 }
107 }
112
108
113 impl fmt::Display for PatternError {
109 impl fmt::Display for PatternError {
114 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
110 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
115 match self {
111 match self {
116 PatternError::UnsupportedSyntax(syntax) => {
112 PatternError::UnsupportedSyntax(syntax) => {
117 write!(f, "Unsupported syntax {}", syntax)
113 write!(f, "Unsupported syntax {}", syntax)
118 }
114 }
119 PatternError::UnsupportedSyntaxInFile(syntax, file_path, line) => {
115 PatternError::UnsupportedSyntaxInFile(syntax, file_path, line) => {
120 write!(
116 write!(
121 f,
117 f,
122 "{}:{}: unsupported syntax {}",
118 "{}:{}: unsupported syntax {}",
123 file_path, line, syntax
119 file_path, line, syntax
124 )
120 )
125 }
121 }
126 PatternError::TooLong(size) => {
122 PatternError::TooLong(size) => {
127 write!(f, "matcher pattern is too long ({} bytes)", size)
123 write!(f, "matcher pattern is too long ({} bytes)", size)
128 }
124 }
129 PatternError::IO(error) => error.fmt(f),
125 PatternError::IO(error) => error.fmt(f),
130 PatternError::Path(error) => error.fmt(f),
126 PatternError::Path(error) => error.fmt(f),
131 PatternError::NonRegexPattern(pattern) => {
127 PatternError::NonRegexPattern(pattern) => {
132 write!(f, "'{:?}' cannot be turned into a regex", pattern)
128 write!(f, "'{:?}' cannot be turned into a regex", pattern)
133 }
129 }
134 }
130 }
135 }
131 }
136 }
132 }
@@ -1,124 +1,118 b''
1 // dirs_multiset.rs
1 // dirs_multiset.rs
2 //
2 //
3 // Copyright 2019 Raphaël Gomès <rgomes@octobus.net>
3 // Copyright 2019 Raphaël Gomès <rgomes@octobus.net>
4 //
4 //
5 // This software may be used and distributed according to the terms of the
5 // This software may be used and distributed according to the terms of the
6 // GNU General Public License version 2 or any later version.
6 // GNU General Public License version 2 or any later version.
7
7
8 //! Bindings for the `hg::dirstate::dirs_multiset` file provided by the
8 //! Bindings for the `hg::dirstate::dirs_multiset` file provided by the
9 //! `hg-core` package.
9 //! `hg-core` package.
10
10
11 use std::cell::RefCell;
11 use std::cell::RefCell;
12
12
13 use cpython::{
13 use cpython::{
14 exc, ObjectProtocol, PyBytes, PyClone, PyDict, PyErr, PyObject, PyResult,
14 exc, ObjectProtocol, PyBytes, PyClone, PyDict, PyErr, PyObject, PyResult,
15 Python, UnsafePyLeaked,
15 Python, UnsafePyLeaked,
16 };
16 };
17
17
18 use hg::{
18 use hg::{
19 utils::hg_path::{HgPath, HgPathBuf},
19 utils::hg_path::{HgPath, HgPathBuf},
20 DirsMultiset, DirsMultisetIter, DirstateMapError,
20 DirsMultiset, DirsMultisetIter,
21 };
21 };
22
22
23 py_class!(pub class Dirs |py| {
23 py_class!(pub class Dirs |py| {
24 @shared data inner: DirsMultiset;
24 @shared data inner: DirsMultiset;
25
25
26 // `map` is either a `dict` or a flat iterator (usually a `set`, sometimes
26 // `map` is either a `dict` or a flat iterator (usually a `set`, sometimes
27 // a `list`)
27 // a `list`)
28 def __new__(
28 def __new__(
29 _cls,
29 _cls,
30 map: PyObject,
30 map: PyObject,
31 ) -> PyResult<Self> {
31 ) -> PyResult<Self> {
32 let inner = if map.cast_as::<PyDict>(py).is_ok() {
32 let inner = if map.cast_as::<PyDict>(py).is_ok() {
33 let err = "pathutil.dirs() with a dict should only be used by the Python dirstatemap \
33 let err = "pathutil.dirs() with a dict should only be used by the Python dirstatemap \
34 and should not be used when Rust is enabled";
34 and should not be used when Rust is enabled";
35 return Err(PyErr::new::<exc::TypeError, _>(py, err.to_string()))
35 return Err(PyErr::new::<exc::TypeError, _>(py, err.to_string()))
36 } else {
36 } else {
37 let map: Result<Vec<HgPathBuf>, PyErr> = map
37 let map: Result<Vec<HgPathBuf>, PyErr> = map
38 .iter(py)?
38 .iter(py)?
39 .map(|o| {
39 .map(|o| {
40 Ok(HgPathBuf::from_bytes(
40 Ok(HgPathBuf::from_bytes(
41 o?.extract::<PyBytes>(py)?.data(py),
41 o?.extract::<PyBytes>(py)?.data(py),
42 ))
42 ))
43 })
43 })
44 .collect();
44 .collect();
45 DirsMultiset::from_manifest(&map?)
45 DirsMultiset::from_manifest(&map?)
46 .map_err(|e| {
46 .map_err(|e| {
47 PyErr::new::<exc::ValueError, _>(py, e.to_string())
47 PyErr::new::<exc::ValueError, _>(py, e.to_string())
48 })?
48 })?
49 };
49 };
50
50
51 Self::create_instance(py, inner)
51 Self::create_instance(py, inner)
52 }
52 }
53
53
54 def addpath(&self, path: PyObject) -> PyResult<PyObject> {
54 def addpath(&self, path: PyObject) -> PyResult<PyObject> {
55 self.inner(py).borrow_mut().add_path(
55 self.inner(py).borrow_mut().add_path(
56 HgPath::new(path.extract::<PyBytes>(py)?.data(py)),
56 HgPath::new(path.extract::<PyBytes>(py)?.data(py)),
57 ).and(Ok(py.None())).or_else(|e| {
57 ).and(Ok(py.None())).or_else(|e| {
58 match e {
58 match e {
59 DirstateMapError::EmptyPath => {
60 Ok(py.None())
61 },
62 e => {
59 e => {
63 Err(PyErr::new::<exc::ValueError, _>(
60 Err(PyErr::new::<exc::ValueError, _>(
64 py,
61 py,
65 e.to_string(),
62 e.to_string(),
66 ))
63 ))
67 }
64 }
68 }
65 }
69 })
66 })
70 }
67 }
71
68
72 def delpath(&self, path: PyObject) -> PyResult<PyObject> {
69 def delpath(&self, path: PyObject) -> PyResult<PyObject> {
73 self.inner(py).borrow_mut().delete_path(
70 self.inner(py).borrow_mut().delete_path(
74 HgPath::new(path.extract::<PyBytes>(py)?.data(py)),
71 HgPath::new(path.extract::<PyBytes>(py)?.data(py)),
75 )
72 )
76 .and(Ok(py.None()))
73 .and(Ok(py.None()))
77 .or_else(|e| {
74 .or_else(|e| {
78 match e {
75 match e {
79 DirstateMapError::EmptyPath => {
80 Ok(py.None())
81 },
82 e => {
76 e => {
83 Err(PyErr::new::<exc::ValueError, _>(
77 Err(PyErr::new::<exc::ValueError, _>(
84 py,
78 py,
85 e.to_string(),
79 e.to_string(),
86 ))
80 ))
87 }
81 }
88 }
82 }
89 })
83 })
90 }
84 }
91 def __iter__(&self) -> PyResult<DirsMultisetKeysIterator> {
85 def __iter__(&self) -> PyResult<DirsMultisetKeysIterator> {
92 let leaked_ref = self.inner(py).leak_immutable();
86 let leaked_ref = self.inner(py).leak_immutable();
93 DirsMultisetKeysIterator::from_inner(
87 DirsMultisetKeysIterator::from_inner(
94 py,
88 py,
95 unsafe { leaked_ref.map(py, |o| o.iter()) },
89 unsafe { leaked_ref.map(py, |o| o.iter()) },
96 )
90 )
97 }
91 }
98
92
99 def __contains__(&self, item: PyObject) -> PyResult<bool> {
93 def __contains__(&self, item: PyObject) -> PyResult<bool> {
100 Ok(self.inner(py).borrow().contains(HgPath::new(
94 Ok(self.inner(py).borrow().contains(HgPath::new(
101 item.extract::<PyBytes>(py)?.data(py),
95 item.extract::<PyBytes>(py)?.data(py),
102 )))
96 )))
103 }
97 }
104 });
98 });
105
99
106 impl Dirs {
100 impl Dirs {
107 pub fn from_inner(py: Python, d: DirsMultiset) -> PyResult<Self> {
101 pub fn from_inner(py: Python, d: DirsMultiset) -> PyResult<Self> {
108 Self::create_instance(py, d)
102 Self::create_instance(py, d)
109 }
103 }
110
104
111 fn translate_key(
105 fn translate_key(
112 py: Python,
106 py: Python,
113 res: &HgPathBuf,
107 res: &HgPathBuf,
114 ) -> PyResult<Option<PyBytes>> {
108 ) -> PyResult<Option<PyBytes>> {
115 Ok(Some(PyBytes::new(py, res.as_bytes())))
109 Ok(Some(PyBytes::new(py, res.as_bytes())))
116 }
110 }
117 }
111 }
118
112
119 py_shared_iterator!(
113 py_shared_iterator!(
120 DirsMultisetKeysIterator,
114 DirsMultisetKeysIterator,
121 UnsafePyLeaked<DirsMultisetIter<'static>>,
115 UnsafePyLeaked<DirsMultisetIter<'static>>,
122 Dirs::translate_key,
116 Dirs::translate_key,
123 Option<PyBytes>
117 Option<PyBytes>
124 );
118 );
General Comments 0
You need to be logged in to leave comments. Login now