History

fix: Don't panic when rev-parsing `^^^` and similar (#1914)

Sebastian Thiel committed 1 year ago

Commit aa8daf81 parent 12cb8477 files · +29 −3Browse files

Unified · Split

7 files
  1. gix/src/revision/spec/parse/delegate/navigate.rs +7 −1
  2. gix/src/revision/spec/parse/error.rs +0 −1
  3. gix/src/revision/spec/parse/types.rs +2 −0
  4. gix/tests/fixtures/generated-archives/make_rev_spec_parse_repos.tar +0 −0
  5. gix/tests/fixtures/make_rev_spec_parse_repos.sh +5 −0
  6. gix/tests/gix/revision/spec/from_bytes/mod.rs +6 −0
  7. gix/tests/gix/revision/spec/from_bytes/traverse.rs +10 −2
gix/src/revision/spec/parse/delegate/navigate.rs+7−1
@@ -25,7 +25,13 @@ impl delegate::Navigate for Delegate<'_> { · 24 unmodified lines
25 25
26 let mut replacements = Replacements::default();26 let mut replacements = Replacements::default();
27 let mut errors = Vec::new();27 let mut errors = Vec::new();
28 let objs = self.objs[self.idx].as_mut()?;28 let objs = match self.objs[self.idx].as_mut() {
29 Some(objs) => objs,
30 None => {
31 self.err.push(Error::TraversalWithoutStartObject);
32 return None;
33 }
34 };
29 let repo = self.repo;35 let repo = self.repo;
30 36
31 for obj in objs.iter() {37 for obj in objs.iter() {
gix/src/revision/spec/parse/error.rs+0−1
@@ -105,7 +105,6 @@ impl Error { · 104 unmodified lines
105 }105 }
106 106
107 pub(crate) fn from_errors(errors: Vec<Self>) -> Self {107 pub(crate) fn from_errors(errors: Vec<Self>) -> Self {
108 assert!(!errors.is_empty());
109 match errors.len() {108 match errors.len() {
110 0 => unreachable!(109 0 => unreachable!(
111 "BUG: cannot create something from nothing, must have recorded some errors to call from_errors()"110 "BUG: cannot create something from nothing, must have recorded some errors to call from_errors()"
gix/src/revision/spec/parse/types.rs+2−0
@@ -188,6 +188,8 @@ pub enum Error { · 187 unmodified lines
188 },188 },
189 #[error(transparent)]189 #[error(transparent)]
190 Traverse(#[from] crate::revision::walk::iter::Error),190 Traverse(#[from] crate::revision::walk::iter::Error),
191 #[error("Tried to navigate the commit-graph without providing an anchor first")]
192 TraversalWithoutStartObject,
191 #[error(transparent)]193 #[error(transparent)]
192 Walk(#[from] crate::revision::walk::Error),194 Walk(#[from] crate::revision::walk::Error),
193 #[error("Spec does not contain a single object id")]195 #[error("Spec does not contain a single object id")]
gix/tests/fixtures/generated-archives/make_rev_spec_parse_repos.tar+0−0

Binary file not shown.

gix/tests/fixtures/make_rev_spec_parse_repos.sh+5−0
@@ -356,6 +356,7 @@ EOF · 355 unmodified lines
356 baseline "@^{/!-B}" # negation from branch356 baseline "@^{/!-B}" # negation from branch
357 baseline ":file" # index lookup, default stage 0357 baseline ":file" # index lookup, default stage 0
358 baseline ":1:file" # stage 1358 baseline ":1:file" # stage 1
359 baseline ":5:file" # invalid stage
359 baseline ":foo" # not found360 baseline ":foo" # not found
360 # parents361 # parents
361 baseline "a"362 baseline "a"
@@ -381,6 +382,10 @@ EOF · 19 unmodified lines
381 baseline "b^3^2"382 baseline "b^3^2"
382 baseline "a^^3^2"383 baseline "a^^3^2"
383 384
385 # invalid
386 baseline "^^"
387 baseline "^^HEAD"
388
384 baseline "@{-1}"389 baseline "@{-1}"
385 baseline "@{-2}"390 baseline "@{-2}"
386 baseline "@{-3}"391 baseline "@{-3}"
gix/tests/gix/revision/spec/from_bytes/mod.rs+6−0
@@ -64,6 +64,12 @@ mod index { · 63 unmodified lines
64 "Path \"file\" did not exist in index at stage 1. It does exist at stage 0. It exists on disk",64 "Path \"file\" did not exist in index at stage 1. It does exist at stage 0. It exists on disk",
65 );65 );
66 66
67 assert_eq!(
68 parse_spec(":5:file", &repo).unwrap_err().to_string(),
69 "Path \"5:file\" did not exist in index at stage 0. It does not exist on disk",
70 "invalid stage ids are interpreted as part of the filename"
71 );
72
67 assert_eq!(73 assert_eq!(
68 parse_spec(":foo", &repo).unwrap_err().to_string(),74 parse_spec(":foo", &repo).unwrap_err().to_string(),
69 "Path \"foo\" did not exist in index at stage 0. It does not exist on disk",75 "Path \"foo\" did not exist in index at stage 0. It does not exist on disk",
gix/tests/gix/revision/spec/from_bytes/traverse.rs+10−2
@@ -24,8 +24,16 @@ fn complex() -> crate::Result { · 23 unmodified lines
24#[test]24#[test]
25fn freestanding_negation_yields_descriptive_error() -> crate::Result {25fn freestanding_negation_yields_descriptive_error() -> crate::Result {
26 let repo = repo("complex_graph")?;26 let repo = repo("complex_graph")?;
27 let expected = "The rev-spec is malformed and misses a ref name";27 for revspec in ["^^", "^^HEAD"] {
28 assert_eq!(parse_spec("^", &repo).unwrap_err().to_string(), expected);28 assert_eq!(
29 parse_spec(revspec, &repo).unwrap_err().to_string(),
30 "Tried to navigate the commit-graph without providing an anchor first"
31 );
32 }
33 assert_eq!(
34 parse_spec("^", &repo).unwrap_err().to_string(),
35 "The rev-spec is malformed and misses a ref name"
36 );
29 assert_eq!(37 assert_eq!(
30 parse_spec("^!", &repo).unwrap_err().to_string(),38 parse_spec("^!", &repo).unwrap_err().to_string(),
31 "The ref partially named \"!\" could not be found"39 "The ref partially named \"!\" could not be found"