Shell: Correct FdRedirection inheriting from two RefCounted bases

Also add missing calls to `adopt()`.
This commit is contained in:
AnotherTest 2020-08-04 14:23:23 +04:30 committed by Andreas Kling
parent 12af65c1c9
commit 1d08cab9ab
Notes: sideshowbarker 2024-07-19 04:19:59 +09:00
5 changed files with 32 additions and 22 deletions

View file

@ -546,7 +546,7 @@ void CloseFdRedirection::dump(int level) const
RefPtr<Value> CloseFdRedirection::run(RefPtr<Shell>) RefPtr<Value> CloseFdRedirection::run(RefPtr<Shell>)
{ {
Command command; Command command;
command.redirections.append(*new CloseRedirection(m_fd)); command.redirections.append(adopt(*new CloseRedirection(m_fd)));
return create<CommandValue>(move(command)); return create<CommandValue>(move(command));
} }
@ -1122,8 +1122,8 @@ RefPtr<Value> Pipe::run(RefPtr<Shell> shell)
auto pipe_write_end = new FdRedirection(STDIN_FILENO, -1, Rewiring::Close::Destination); auto pipe_write_end = new FdRedirection(STDIN_FILENO, -1, Rewiring::Close::Destination);
auto pipe_read_end = new FdRedirection(STDOUT_FILENO, -1, pipe_write_end, Rewiring::Close::RefreshDestination); auto pipe_read_end = new FdRedirection(STDOUT_FILENO, -1, pipe_write_end, Rewiring::Close::RefreshDestination);
first_in_right.redirections.append(*pipe_write_end); first_in_right.redirections.append(adopt(*pipe_write_end));
last_in_left.redirections.append(*pipe_read_end); last_in_left.redirections.append(adopt(*pipe_read_end));
last_in_left.should_wait = false; last_in_left.should_wait = false;
last_in_left.is_pipe_source = true; last_in_left.is_pipe_source = true;
@ -1238,7 +1238,7 @@ RefPtr<Value> ReadRedirection::run(RefPtr<Shell> shell)
StringBuilder builder; StringBuilder builder;
builder.join(" ", path_segments); builder.join(" ", path_segments);
command.redirections.append(*new PathRedirection(builder.to_string(), m_fd, PathRedirection::Read)); command.redirections.append(adopt(*new PathRedirection(builder.to_string(), m_fd, PathRedirection::Read)));
return create<CommandValue>(move(command)); return create<CommandValue>(move(command));
} }
@ -1265,7 +1265,7 @@ RefPtr<Value> ReadWriteRedirection::run(RefPtr<Shell> shell)
StringBuilder builder; StringBuilder builder;
builder.join(" ", path_segments); builder.join(" ", path_segments);
command.redirections.append(*new PathRedirection(builder.to_string(), m_fd, PathRedirection::ReadWrite)); command.redirections.append(adopt(*new PathRedirection(builder.to_string(), m_fd, PathRedirection::ReadWrite)));
return create<CommandValue>(move(command)); return create<CommandValue>(move(command));
} }
@ -1758,7 +1758,7 @@ RefPtr<Value> WriteAppendRedirection::run(RefPtr<Shell> shell)
StringBuilder builder; StringBuilder builder;
builder.join(" ", path_segments); builder.join(" ", path_segments);
command.redirections.append(*new PathRedirection(builder.to_string(), m_fd, PathRedirection::WriteAppend)); command.redirections.append(adopt(*new PathRedirection(builder.to_string(), m_fd, PathRedirection::WriteAppend)));
return create<CommandValue>(move(command)); return create<CommandValue>(move(command));
} }
@ -1785,7 +1785,7 @@ RefPtr<Value> WriteRedirection::run(RefPtr<Shell> shell)
StringBuilder builder; StringBuilder builder;
builder.join(" ", path_segments); builder.join(" ", path_segments);
command.redirections.append(*new PathRedirection(builder.to_string(), m_fd, PathRedirection::Write)); command.redirections.append(adopt(*new PathRedirection(builder.to_string(), m_fd, PathRedirection::Write)));
return create<CommandValue>(move(command)); return create<CommandValue>(move(command));
} }

View file

@ -48,10 +48,11 @@ struct Position {
bool contains(size_t offset) const { return start_offset <= offset && offset <= end_offset; } bool contains(size_t offset) const { return start_offset <= offset && offset <= end_offset; }
}; };
struct FdRedirection;
struct Rewiring : public RefCounted<Rewiring> { struct Rewiring : public RefCounted<Rewiring> {
int source_fd { -1 }; int source_fd { -1 };
int dest_fd { -1 }; int dest_fd { -1 };
Rewiring* other_pipe_end { nullptr }; FdRedirection* other_pipe_end { nullptr };
enum class Close { enum class Close {
None, None,
Source, Source,
@ -67,7 +68,7 @@ struct Rewiring : public RefCounted<Rewiring> {
{ {
} }
Rewiring(int source, int dest, Rewiring* other_end, Close close) Rewiring(int source, int dest, FdRedirection* other_end, Close close)
: source_fd(source) : source_fd(source)
, dest_fd(dest) , dest_fd(dest)
, other_pipe_end(other_end) , other_pipe_end(other_end)
@ -121,20 +122,30 @@ private:
virtual bool is_path_redirection() const override { return true; } virtual bool is_path_redirection() const override { return true; }
}; };
struct FdRedirection : public Redirection struct FdRedirection : public Redirection {
, public Rewiring { virtual Result<RefPtr<Rewiring>, String> apply() const override
{
virtual Result<RefPtr<Rewiring>, String> apply() const override { return static_cast<RefPtr<Rewiring>>(this); } return RefPtr<Rewiring>(adopt(*new Rewiring(source_fd, dest_fd, other_pipe_end, action)));
}
virtual ~FdRedirection(); virtual ~FdRedirection();
FdRedirection(int source, int dest, Rewiring::Close close) FdRedirection(int source, int dest, Rewiring::Close close)
: Rewiring(source, dest, close) : FdRedirection(source, dest, nullptr, close)
{ {
} }
FdRedirection(int source, int dest, Rewiring* pipe_end, Rewiring::Close close)
: Rewiring(source, dest, pipe_end, close) FdRedirection(int source, int dest, FdRedirection* pipe_end, Rewiring::Close close)
: source_fd(source)
, dest_fd(dest)
, other_pipe_end(pipe_end)
, action(close)
{ {
} }
int source_fd { -1 };
int dest_fd { -1 };
FdRedirection* other_pipe_end { nullptr };
Rewiring::Close action { Rewiring::Close::None };
private: private:
virtual bool is_fd_redirection() const override { return true; } virtual bool is_fd_redirection() const override { return true; }
}; };

View file

@ -698,7 +698,7 @@ int Shell::builtin_shift(int argc, const char** argv)
} }
if (!argv_->is_list()) if (!argv_->is_list())
argv_ = *new AST::ListValue({ argv_ }); argv_ = adopt(*new AST::ListValue({ argv_ }));
auto& values = static_cast<AST::ListValue*>(argv_.ptr())->values(); auto& values = static_cast<AST::ListValue*>(argv_.ptr())->values();
if ((size_t)count > values.size()) { if ((size_t)count > values.size()) {

View file

@ -287,8 +287,8 @@ Vector<AST::Command> Shell::expand_aliases(Vector<AST::Command> initial_commands
auto* ast = static_cast<AST::Execute*>(subcommand_ast.ptr()); auto* ast = static_cast<AST::Execute*>(subcommand_ast.ptr());
subcommand_ast = ast->command(); subcommand_ast = ast->command();
} }
AST::Node& substitute = *new AST::Join(subcommand_ast->position(), subcommand_ast, *new AST::CommandLiteral(subcommand_ast->position(), command)); RefPtr<AST::Node> substitute = adopt(*new AST::Join(subcommand_ast->position(), subcommand_ast, adopt(*new AST::CommandLiteral(subcommand_ast->position(), command))));
for (auto& subst_command : substitute.run(*this)->resolve_as_commands(*this)) { for (auto& subst_command : substitute->run(*this)->resolve_as_commands(*this)) {
if (!subst_command.argv.is_empty() && subst_command.argv.first() == argv0) // Disallow an alias resolving to itself. if (!subst_command.argv.is_empty() && subst_command.argv.first() == argv0) // Disallow an alias resolving to itself.
commands.append(subst_command); commands.append(subst_command);
else else
@ -596,8 +596,7 @@ Vector<RefPtr<Job>> Shell::run_commands(Vector<AST::Command>& commands)
auto path_redir = (const AST::PathRedirection*)redir.ptr(); auto path_redir = (const AST::PathRedirection*)redir.ptr();
dbg() << "redir path " << (int)path_redir->direction << " " << path_redir->path << " <-> " << path_redir->fd; dbg() << "redir path " << (int)path_redir->direction << " " << path_redir->path << " <-> " << path_redir->fd;
} else if (redir->is_fd_redirection()) { } else if (redir->is_fd_redirection()) {
auto fd_redir = (const AST::FdRedirection*)redir.ptr(); dbg() << "redir fd " << redir->source_fd << " -> " << redir->dest_fd;
dbg() << "redir fd " << fd_redir->source_fd << " -> " << fd_redir->dest_fd;
} else if (redir->is_close_redirection()) { } else if (redir->is_close_redirection()) {
auto close_redir = (const AST::CloseRedirection*)redir.ptr(); auto close_redir = (const AST::CloseRedirection*)redir.ptr();
dbg() << "close fd " << close_redir->fd; dbg() << "close fd " << close_redir->fd;

View file

@ -187,7 +187,7 @@ int main(int argc, char** argv)
Vector<String> args; Vector<String> args;
for (auto* arg : script_args) for (auto* arg : script_args)
args.empend(arg); args.empend(arg);
shell->set_local_variable("ARGV", *new AST::ListValue(move(args))); shell->set_local_variable("ARGV", adopt(*new AST::ListValue(move(args))));
} }
if (command_to_run) { if (command_to_run) {