From 5b136d450f26a520f335e175708056255d6be2e6 Mon Sep 17 00:00:00 2001 From: 99jte <78996170+99jte@users.noreply.github.com> Date: Sun, 13 Aug 2023 05:01:32 -0700 Subject: [PATCH] Include the target of bad redirects in the error (#9947) Fixes #8877 --- fish-rust/src/ast.rs | 9 +++++++++ fish-rust/src/parse_constants.rs | 12 ++++++++++++ src/fish_tests.cpp | 5 +++++ 3 files changed, 26 insertions(+) diff --git a/fish-rust/src/ast.rs b/fish-rust/src/ast.rs index 432cc689a..60eb7469c 100644 --- a/fish-rust/src/ast.rs +++ b/fish-rust/src/ast.rs @@ -3192,6 +3192,15 @@ fn consume_excess_token_generating_error(&mut self) { } } } + ParseTokenType::redirection if self.peek_type(0) == ParseTokenType::string => { + let next = self.tokens.pop(); + parse_error_range!( + self, + next.range().combine(tok.range()), + ParseErrorCode::generic, + "Expected a string, but found a redirection" + ); + } ParseTokenType::pipe | ParseTokenType::redirection | ParseTokenType::background diff --git a/fish-rust/src/parse_constants.rs b/fish-rust/src/parse_constants.rs index 5cf37e016..aa876d5cd 100644 --- a/fish-rust/src/parse_constants.rs +++ b/fish-rust/src/parse_constants.rs @@ -237,6 +237,18 @@ pub fn end(&self) -> usize { .try_into() .unwrap() } + pub fn combine(&self, other: Self) -> Self { + let start = std::cmp::min(self.start, other.start); + SourceRange { + start, + length: std::cmp::max(self.end(), other.end()) + .checked_sub(start.try_into().unwrap()) + .expect("Overflow") + .try_into() + .unwrap(), + } + } + fn end_ffi(&self) -> u32 { self.start.checked_add(self.length).expect("Overflow") } diff --git a/src/fish_tests.cpp b/src/fish_tests.cpp index 724f4ea98..c7287a11b 100644 --- a/src/fish_tests.cpp +++ b/src/fish_tests.cpp @@ -4883,6 +4883,11 @@ static void test_highlighting() { }); #endif + highlight_tests.push_back({ + {L">", highlight_role_t::error}, + {L"echo", highlight_role_t::error}, + }); + bool saved_flag = feature_test(feature_flag_t::ampersand_nobg_in_token); feature_set(feature_flag_t::ampersand_nobg_in_token, true); for (const highlight_component_list_t &components : highlight_tests) {