mirror of
https://github.com/fish-shell/fish-shell.git
synced 2025-02-09 01:23:59 +08:00
Back out "Support help argument in "{ -h""
This backs out commit efce176ceb
.
This commit is contained in:
parent
d3c37de753
commit
8208a12a76
|
@ -8,8 +8,6 @@ function __fish_print_help --description "Print help message for the specified f
|
||||||
set item true
|
set item true
|
||||||
case '['
|
case '['
|
||||||
set item test
|
set item test
|
||||||
case '{'
|
|
||||||
set item begin
|
|
||||||
end
|
end
|
||||||
|
|
||||||
# Do nothing if the file does not exist
|
# Do nothing if the file does not exist
|
||||||
|
|
125
src/ast.rs
125
src/ast.rs
|
@ -71,7 +71,6 @@ trait NodeVisitorMut {
|
||||||
&mut self,
|
&mut self,
|
||||||
_node: &mut BlockStatementHeaderVariant,
|
_node: &mut BlockStatementHeaderVariant,
|
||||||
) -> VisitResult;
|
) -> VisitResult;
|
||||||
fn visit_command_token(&mut self, _node: &mut CommandTokenVariant) -> VisitResult;
|
|
||||||
fn visit_statement(&mut self, _node: &mut StatementVariant) -> VisitResult;
|
fn visit_statement(&mut self, _node: &mut StatementVariant) -> VisitResult;
|
||||||
|
|
||||||
fn visit_decorated_statement_decorator(
|
fn visit_decorated_statement_decorator(
|
||||||
|
@ -180,9 +179,6 @@ pub trait ConcreteNode {
|
||||||
fn as_argument_or_redirection_list(&self) -> Option<&ArgumentOrRedirectionList> {
|
fn as_argument_or_redirection_list(&self) -> Option<&ArgumentOrRedirectionList> {
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
fn as_command_token(&self) -> Option<&CommandToken> {
|
|
||||||
None
|
|
||||||
}
|
|
||||||
fn as_statement(&self) -> Option<&Statement> {
|
fn as_statement(&self) -> Option<&Statement> {
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
|
@ -304,9 +300,6 @@ trait ConcreteNodeMut {
|
||||||
fn as_mut_argument_or_redirection_list(&mut self) -> Option<&mut ArgumentOrRedirectionList> {
|
fn as_mut_argument_or_redirection_list(&mut self) -> Option<&mut ArgumentOrRedirectionList> {
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
fn as_mut_command_token(&mut self) -> Option<&mut CommandToken> {
|
|
||||||
None
|
|
||||||
}
|
|
||||||
fn as_mut_statement(&mut self) -> Option<&mut Statement> {
|
fn as_mut_statement(&mut self) -> Option<&mut Statement> {
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
|
@ -930,9 +923,6 @@ macro_rules! visit_variant_field_mut {
|
||||||
(BlockStatementHeaderVariant, $visitor:ident, $field:expr) => {
|
(BlockStatementHeaderVariant, $visitor:ident, $field:expr) => {
|
||||||
$visitor.visit_block_statement_header(&mut $field)
|
$visitor.visit_block_statement_header(&mut $field)
|
||||||
};
|
};
|
||||||
(CommandTokenVariant, $visitor:ident, $field:expr) => {
|
|
||||||
$visitor.visit_command_token(&mut $field)
|
|
||||||
};
|
|
||||||
(StatementVariant, $visitor:ident, $field:expr) => {
|
(StatementVariant, $visitor:ident, $field:expr) => {
|
||||||
$visitor.visit_statement(&mut $field)
|
$visitor.visit_statement(&mut $field)
|
||||||
};
|
};
|
||||||
|
@ -1033,19 +1023,6 @@ macro_rules! set_parent_of_union_field {
|
||||||
$self.$field_name.as_mut_redirection().set_parents();
|
$self.$field_name.as_mut_redirection().set_parents();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
(
|
|
||||||
$self:ident,
|
|
||||||
$field_name:ident,
|
|
||||||
CommandTokenVariant
|
|
||||||
) => {
|
|
||||||
if matches!($self.$field_name, CommandTokenVariant::LeftBrace(_)) {
|
|
||||||
$self.$field_name.as_mut_left_brace().parent = Some($self);
|
|
||||||
$self.$field_name.as_mut_left_brace().set_parents();
|
|
||||||
} else {
|
|
||||||
$self.$field_name.as_mut_string().parent = Some($self);
|
|
||||||
$self.$field_name.as_mut_string().set_parents();
|
|
||||||
}
|
|
||||||
};
|
|
||||||
(
|
(
|
||||||
$self:ident,
|
$self:ident,
|
||||||
$field_name:ident,
|
$field_name:ident,
|
||||||
|
@ -1187,38 +1164,6 @@ impl ConcreteNodeMut for ArgumentOrRedirectionList {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Default, Debug)]
|
|
||||||
pub struct CommandToken {
|
|
||||||
parent: Option<*const dyn Node>,
|
|
||||||
pub contents: CommandTokenVariant,
|
|
||||||
}
|
|
||||||
implement_node!(CommandToken, branch, command_token);
|
|
||||||
implement_acceptor_for_branch!(
|
|
||||||
CommandToken,
|
|
||||||
(contents: (variant<CommandTokenVariant>))
|
|
||||||
);
|
|
||||||
impl ConcreteNode for CommandToken {
|
|
||||||
fn as_command_token(&self) -> Option<&CommandToken> {
|
|
||||||
Some(self)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
impl ConcreteNodeMut for CommandToken {
|
|
||||||
fn as_mut_command_token(&mut self) -> Option<&mut CommandToken> {
|
|
||||||
Some(self)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
impl CheckParse for CommandToken {
|
|
||||||
fn can_be_parsed(pop: &mut Populator<'_>) -> bool {
|
|
||||||
let typ = pop.peek_type(0);
|
|
||||||
matches!(typ, ParseTokenType::string | ParseTokenType::left_brace)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
impl CommandToken {
|
|
||||||
pub fn is_left_brace(&self) -> bool {
|
|
||||||
matches!(&self.contents, CommandTokenVariant::LeftBrace(_))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// A statement is a normal command, or an if / while / etc
|
/// A statement is a normal command, or an if / while / etc
|
||||||
#[derive(Default, Debug)]
|
#[derive(Default, Debug)]
|
||||||
pub struct Statement {
|
pub struct Statement {
|
||||||
|
@ -1707,7 +1652,7 @@ pub struct DecoratedStatement {
|
||||||
/// An optional decoration (command, builtin, exec, etc).
|
/// An optional decoration (command, builtin, exec, etc).
|
||||||
pub opt_decoration: Option<DecoratedStatementDecorator>,
|
pub opt_decoration: Option<DecoratedStatementDecorator>,
|
||||||
/// Command to run.
|
/// Command to run.
|
||||||
pub command: CommandToken,
|
pub command: String_,
|
||||||
/// Args and redirs
|
/// Args and redirs
|
||||||
pub args_or_redirs: ArgumentOrRedirectionList,
|
pub args_or_redirs: ArgumentOrRedirectionList,
|
||||||
}
|
}
|
||||||
|
@ -1715,7 +1660,7 @@ implement_node!(DecoratedStatement, branch, decorated_statement);
|
||||||
implement_acceptor_for_branch!(
|
implement_acceptor_for_branch!(
|
||||||
DecoratedStatement,
|
DecoratedStatement,
|
||||||
(opt_decoration: (Option<DecoratedStatementDecorator>)),
|
(opt_decoration: (Option<DecoratedStatementDecorator>)),
|
||||||
(command: (CommandToken)),
|
(command: (String_)),
|
||||||
(args_or_redirs: (ArgumentOrRedirectionList)),
|
(args_or_redirs: (ArgumentOrRedirectionList)),
|
||||||
);
|
);
|
||||||
impl ConcreteNode for DecoratedStatement {
|
impl ConcreteNode for DecoratedStatement {
|
||||||
|
@ -2226,56 +2171,6 @@ impl ArgumentOrRedirection {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
|
||||||
pub enum CommandTokenVariant {
|
|
||||||
String(String_),
|
|
||||||
LeftBrace(TokenLeftBrace),
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Default for CommandTokenVariant {
|
|
||||||
fn default() -> Self {
|
|
||||||
CommandTokenVariant::String(String_::default())
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Acceptor for CommandTokenVariant {
|
|
||||||
fn accept<'a>(&'a self, visitor: &mut dyn NodeVisitor<'a>, reversed: bool) {
|
|
||||||
match self {
|
|
||||||
CommandTokenVariant::String(child) => child.accept(visitor, reversed),
|
|
||||||
CommandTokenVariant::LeftBrace(child) => child.accept(visitor, reversed),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
impl AcceptorMut for CommandTokenVariant {
|
|
||||||
fn accept_mut(&mut self, visitor: &mut dyn NodeVisitorMut, reversed: bool) {
|
|
||||||
match self {
|
|
||||||
CommandTokenVariant::String(child) => child.accept_mut(visitor, reversed),
|
|
||||||
CommandTokenVariant::LeftBrace(child) => child.accept_mut(visitor, reversed),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl CommandTokenVariant {
|
|
||||||
pub fn embedded_node(&self) -> &dyn Node {
|
|
||||||
match self {
|
|
||||||
CommandTokenVariant::String(node) => node,
|
|
||||||
CommandTokenVariant::LeftBrace(node) => node,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fn as_mut_string(&mut self) -> &mut String_ {
|
|
||||||
match self {
|
|
||||||
CommandTokenVariant::String(node) => node,
|
|
||||||
_ => panic!(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fn as_mut_left_brace(&mut self) -> &mut TokenLeftBrace {
|
|
||||||
match self {
|
|
||||||
CommandTokenVariant::LeftBrace(node) => node,
|
|
||||||
_ => panic!(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub enum BlockStatementHeaderVariant {
|
pub enum BlockStatementHeaderVariant {
|
||||||
None,
|
None,
|
||||||
|
@ -2530,7 +2425,6 @@ pub fn ast_type_to_string(t: Type) -> &'static wstr {
|
||||||
Type::variable_assignment_list => L!("variable_assignment_list"),
|
Type::variable_assignment_list => L!("variable_assignment_list"),
|
||||||
Type::argument_or_redirection => L!("argument_or_redirection"),
|
Type::argument_or_redirection => L!("argument_or_redirection"),
|
||||||
Type::argument_or_redirection_list => L!("argument_or_redirection_list"),
|
Type::argument_or_redirection_list => L!("argument_or_redirection_list"),
|
||||||
Type::command_token => L!("command_token"),
|
|
||||||
Type::statement => L!("statement"),
|
Type::statement => L!("statement"),
|
||||||
Type::job_pipeline => L!("job_pipeline"),
|
Type::job_pipeline => L!("job_pipeline"),
|
||||||
Type::job_conjunction => L!("job_conjunction"),
|
Type::job_conjunction => L!("job_conjunction"),
|
||||||
|
@ -3211,17 +3105,6 @@ impl<'s> NodeVisitorMut for Populator<'s> {
|
||||||
*node = self.allocate_populate_block_header();
|
*node = self.allocate_populate_block_header();
|
||||||
VisitResult::Continue(())
|
VisitResult::Continue(())
|
||||||
}
|
}
|
||||||
fn visit_command_token(&mut self, node: &mut CommandTokenVariant) -> VisitResult {
|
|
||||||
if let Some(lbrace) = self.try_parse::<TokenLeftBrace>() {
|
|
||||||
*node = CommandTokenVariant::LeftBrace(*lbrace);
|
|
||||||
} else if let Some(s) = self.try_parse::<String_>() {
|
|
||||||
*node = CommandTokenVariant::String(*s);
|
|
||||||
} else {
|
|
||||||
// On error, we return an unsourced decorated statement.
|
|
||||||
*node = CommandTokenVariant::String(Default::default());
|
|
||||||
}
|
|
||||||
ControlFlow::Continue(())
|
|
||||||
}
|
|
||||||
fn visit_statement(&mut self, node: &mut StatementVariant) -> VisitResult {
|
fn visit_statement(&mut self, node: &mut StatementVariant) -> VisitResult {
|
||||||
*node = self.allocate_populate_statement_contents();
|
*node = self.allocate_populate_statement_contents();
|
||||||
VisitResult::Continue(())
|
VisitResult::Continue(())
|
||||||
|
@ -3770,9 +3653,6 @@ impl<'s> Populator<'s> {
|
||||||
// Construct a decorated statement, which will be unsourced.
|
// Construct a decorated statement, which will be unsourced.
|
||||||
self.allocate_visit::<DecoratedStatement>();
|
self.allocate_visit::<DecoratedStatement>();
|
||||||
} else if self.peek_token(0).typ == ParseTokenType::left_brace {
|
} else if self.peek_token(0).typ == ParseTokenType::left_brace {
|
||||||
if self.peek_token(1).is_help_argument {
|
|
||||||
return new_decorated_statement(self);
|
|
||||||
}
|
|
||||||
let embedded = self.allocate_visit::<BraceStatement>();
|
let embedded = self.allocate_visit::<BraceStatement>();
|
||||||
return StatementVariant::BraceStatement(embedded);
|
return StatementVariant::BraceStatement(embedded);
|
||||||
} else if self.peek_token(0).typ != ParseTokenType::string {
|
} else if self.peek_token(0).typ != ParseTokenType::string {
|
||||||
|
@ -4254,7 +4134,6 @@ pub enum Type {
|
||||||
variable_assignment_list,
|
variable_assignment_list,
|
||||||
argument_or_redirection,
|
argument_or_redirection,
|
||||||
argument_or_redirection_list,
|
argument_or_redirection_list,
|
||||||
command_token,
|
|
||||||
statement,
|
statement,
|
||||||
job_pipeline,
|
job_pipeline,
|
||||||
job_conjunction,
|
job_conjunction,
|
||||||
|
|
|
@ -342,7 +342,6 @@ impl<'source, 'ast> PrettyPrinterState<'source, 'ast> {
|
||||||
// Allow escaped newlines before commands that follow a variable assignment
|
// Allow escaped newlines before commands that follow a variable assignment
|
||||||
// since both can be long (#7955).
|
// since both can be long (#7955).
|
||||||
let p = node.parent().unwrap();
|
let p = node.parent().unwrap();
|
||||||
let p = p.parent().unwrap();
|
|
||||||
if p.typ() != Type::decorated_statement {
|
if p.typ() != Type::decorated_statement {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
|
@ -415,17 +415,12 @@ pub fn builtin_run(parser: &Parser, argv: &mut [&wstr], streams: &mut IoStreams)
|
||||||
return ProcStatus::from_exit_code(STATUS_CMD_OK.unwrap());
|
return ProcStatus::from_exit_code(STATUS_CMD_OK.unwrap());
|
||||||
}
|
}
|
||||||
|
|
||||||
let builtin_func = if argv[0] == L!("{") {
|
let Some(builtin) = builtin_lookup(argv[0]) else {
|
||||||
builtin_generic
|
FLOGF!(error, "%s", wgettext_fmt!(UNKNOWN_BUILTIN_ERR_MSG, argv[0]));
|
||||||
} else {
|
return ProcStatus::from_exit_code(STATUS_CMD_ERROR.unwrap());
|
||||||
let Some(builtin) = builtin_lookup(argv[0]) else {
|
|
||||||
FLOGF!(error, "%s", wgettext_fmt!(UNKNOWN_BUILTIN_ERR_MSG, argv[0]));
|
|
||||||
return ProcStatus::from_exit_code(STATUS_CMD_ERROR.unwrap());
|
|
||||||
};
|
|
||||||
builtin.func
|
|
||||||
};
|
};
|
||||||
|
|
||||||
let builtin_ret = (builtin_func)(parser, streams, argv);
|
let builtin_ret = (builtin.func)(parser, streams, argv);
|
||||||
|
|
||||||
// Flush our out and error streams, and check for their errors.
|
// Flush our out and error streams, and check for their errors.
|
||||||
let out_ret = streams.out.flush_and_check_error();
|
let out_ret = streams.out.flush_and_check_error();
|
||||||
|
|
|
@ -753,7 +753,7 @@ impl<'s> Highlighter<'s> {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Color a command.
|
// Color a command.
|
||||||
fn color_command(&mut self, node: &ast::CommandToken) {
|
fn color_command(&mut self, node: &ast::String_) {
|
||||||
let source_range = node.source_range();
|
let source_range = node.source_range();
|
||||||
let cmd_str = self.get_source(source_range);
|
let cmd_str = self.get_source(source_range);
|
||||||
|
|
||||||
|
|
|
@ -486,7 +486,7 @@ impl<'a> ExecutionContext {
|
||||||
|
|
||||||
// Get the unexpanded command string. We expect to always get it here.
|
// Get the unexpanded command string. We expect to always get it here.
|
||||||
let unexp_cmd = self.node_source(&statement.command);
|
let unexp_cmd = self.node_source(&statement.command);
|
||||||
let pos_of_command_token = statement.command.try_source_range().unwrap().start();
|
let pos_of_command_token = statement.command.range().unwrap().start();
|
||||||
|
|
||||||
// Expand the string to produce completions, and report errors.
|
// Expand the string to produce completions, and report errors.
|
||||||
let expand_err = expand_to_command_and_args(
|
let expand_err = expand_to_command_and_args(
|
||||||
|
@ -733,29 +733,23 @@ impl<'a> ExecutionContext {
|
||||||
// Get the command and any arguments due to expanding the command.
|
// Get the command and any arguments due to expanding the command.
|
||||||
let mut cmd = WString::new();
|
let mut cmd = WString::new();
|
||||||
let mut args_from_cmd_expansion = vec![];
|
let mut args_from_cmd_expansion = vec![];
|
||||||
let mut process_type = if statement.command.is_left_brace() {
|
let ret = self.expand_command(ctx, statement, &mut cmd, &mut args_from_cmd_expansion);
|
||||||
cmd = L!("{").to_owned();
|
if ret != EndExecutionReason::ok {
|
||||||
ProcessType::builtin
|
return ret;
|
||||||
} else {
|
}
|
||||||
let ret = self.expand_command(ctx, statement, &mut cmd, &mut args_from_cmd_expansion);
|
|
||||||
if ret != EndExecutionReason::ok {
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
// For no-exec, having an empty command is okay. We can't do anything more with it tho.
|
// For no-exec, having an empty command is okay. We can't do anything more with it tho.
|
||||||
if no_exec() {
|
if no_exec() {
|
||||||
return EndExecutionReason::ok;
|
return EndExecutionReason::ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
assert!(
|
assert!(
|
||||||
!cmd.is_empty(),
|
!cmd.is_empty(),
|
||||||
"expand_command should not produce an empty command",
|
"expand_command should not produce an empty command",
|
||||||
);
|
);
|
||||||
|
|
||||||
// Determine the process type.
|
|
||||||
self.process_type_for_command(ctx, statement, &cmd)
|
|
||||||
};
|
|
||||||
|
|
||||||
|
// Determine the process type.
|
||||||
|
let mut process_type = self.process_type_for_command(ctx, statement, &cmd);
|
||||||
let external_cmd = if [ProcessType::external, ProcessType::exec].contains(&process_type) {
|
let external_cmd = if [ProcessType::external, ProcessType::exec].contains(&process_type) {
|
||||||
let parser = ctx.parser();
|
let parser = ctx.parser();
|
||||||
// Determine the actual command. This may be an implicit cd.
|
// Determine the actual command. This may be an implicit cd.
|
||||||
|
|
|
@ -1679,7 +1679,7 @@ fn detect_errors_in_decorated_statement(
|
||||||
}
|
}
|
||||||
|
|
||||||
let unexp_command = com;
|
let unexp_command = com;
|
||||||
if !unexp_command.is_empty() && !dst.command.is_left_brace() {
|
if !unexp_command.is_empty() {
|
||||||
// Check that we can expand the command.
|
// Check that we can expand the command.
|
||||||
// Make a new error list so we can fix the offset for just those, then append later.
|
// Make a new error list so we can fix the offset for just those, then append later.
|
||||||
let mut new_errors = ParseErrorList::new();
|
let mut new_errors = ParseErrorList::new();
|
||||||
|
|
|
@ -5315,7 +5315,7 @@ fn extract_tokens(s: &wstr) -> Vec<PositionedToken> {
|
||||||
let mut cursor = Some(node);
|
let mut cursor = Some(node);
|
||||||
while let Some(cur) = cursor {
|
while let Some(cur) = cursor {
|
||||||
if let Some(stmt) = cur.as_decorated_statement() {
|
if let Some(stmt) = cur.as_decorated_statement() {
|
||||||
if node.pointer_eq(stmt.command.contents.embedded_node()) {
|
if node.pointer_eq(&stmt.command) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -496,7 +496,6 @@ fn test_new_parser_ll2() {
|
||||||
validate!("command", "command", "", StatementDecoration::none);
|
validate!("command", "command", "", StatementDecoration::none);
|
||||||
validate!("command -", "command", "-", StatementDecoration::none);
|
validate!("command -", "command", "-", StatementDecoration::none);
|
||||||
validate!("command --", "command", "--", StatementDecoration::none);
|
validate!("command --", "command", "--", StatementDecoration::none);
|
||||||
validate!("{ -h", "{", "-h", StatementDecoration::none);
|
|
||||||
validate!(
|
validate!(
|
||||||
"builtin --names",
|
"builtin --names",
|
||||||
"builtin",
|
"builtin",
|
||||||
|
|
|
@ -187,26 +187,10 @@ PATH= "{"
|
||||||
# CHECKERR: PATH= "{"
|
# CHECKERR: PATH= "{"
|
||||||
# CHECKERR: ^~^
|
# CHECKERR: ^~^
|
||||||
|
|
||||||
$fish -c '{ -h'
|
|
||||||
# CHECKERR: fish: '{': missing man page
|
|
||||||
# CHECKERR: Documentation may not be installed.
|
|
||||||
# CHECKERR: `help '{'` will show an online version
|
|
||||||
|
|
||||||
PATH= "{" -h
|
|
||||||
# CHECKERR: fish: Unknown command: '{'
|
|
||||||
# CHECKERR: {{.*}}/braces.fish (line {{\d+}}):
|
|
||||||
# CHECKERR: PATH= "{" -h
|
|
||||||
# CHECKERR: ^~^
|
|
||||||
|
|
||||||
$fish -c 'builtin {'
|
$fish -c 'builtin {'
|
||||||
# CHECKERR: fish: Expected end of the statement, but found a '{'
|
# CHECKERR: fish: Expected end of the statement, but found a '{'
|
||||||
# CHECKERR: builtin {
|
# CHECKERR: builtin {
|
||||||
# CHECKERR: ^
|
# CHECKERR: ^
|
||||||
|
|
||||||
$fish -c 'builtin "{"'
|
|
||||||
# CHECKERR: fish: Unknown builtin '"{"'
|
|
||||||
# CHECKERR: builtin "{"
|
|
||||||
# CHECKERR: ^~~~~~~~~~^
|
|
||||||
|
|
||||||
$fish -c 'command {'
|
$fish -c 'command {'
|
||||||
# CHECKERR: fish: Expected end of the statement, but found a '{'
|
# CHECKERR: fish: Expected end of the statement, but found a '{'
|
||||||
|
|
|
@ -482,9 +482,6 @@ level 2 } }
|
||||||
# CHECK: {{^ level 2$}}
|
# CHECK: {{^ level 2$}}
|
||||||
# CHECK: {{^ \}$}}
|
# CHECK: {{^ \}$}}
|
||||||
# CHECK: {{^\}$}}
|
# CHECK: {{^\}$}}
|
||||||
|
|
||||||
echo '{ -h'
|
|
||||||
# CHECK: { -h
|
|
||||||
} | $fish_indent
|
} | $fish_indent
|
||||||
|
|
||||||
echo 'multiline-\\
|
echo 'multiline-\\
|
||||||
|
|
Loading…
Reference in New Issue
Block a user