1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-25 23:37:35 +00:00

Shell: Avoid messing with sigaction while waiting for a child

This commit is contained in:
AnotherTest 2020-05-26 18:45:19 +04:30 committed by Andreas Kling
parent 70a213a6ec
commit d5e9213683
3 changed files with 10 additions and 11 deletions

View file

@ -1024,21 +1024,15 @@ ContinuationRequest Shell::is_complete(const Vector<Command>& commands)
IterationDecision Shell::wait_for_pid(const Shell::SpawnedProcess& process, bool is_first_command_in_chain, int& return_value) IterationDecision Shell::wait_for_pid(const Shell::SpawnedProcess& process, bool is_first_command_in_chain, int& return_value)
{ {
// Disable signal handler for the first command, as we actively wait for it if (is_first_command_in_chain)
sighandler_t chld_handler = nullptr; m_waiting_for_pid = process.pid;
if (is_first_command_in_chain) {
chld_handler = signal(SIGCHLD, nullptr);
dbg() << "Waiting for " << process.name;
}
int wstatus = 0; int wstatus = 0;
int rc = waitpid(process.pid, &wstatus, WSTOPPED); int rc = waitpid(process.pid, &wstatus, WSTOPPED);
auto errno_save = errno; auto errno_save = errno;
if (is_first_command_in_chain) { if (is_first_command_in_chain)
signal(SIGCHLD, chld_handler); m_waiting_for_pid = -1;
dbg() << process.name << " is probably dead now (" << rc << ", " << strerror(errno_save) << ") -> exited " << WIFEXITED(wstatus) << " stopped " << WIFSTOPPED(wstatus);
}
errno = errno_save; errno = errno_save;
if (rc < 0 && errno != EINTR) { if (rc < 0 && errno != EINTR) {

View file

@ -115,6 +115,8 @@ public:
void highlight(Line::Editor&) const; void highlight(Line::Editor&) const;
Vector<Line::CompletionSuggestion> complete(const Line::Editor&); Vector<Line::CompletionSuggestion> complete(const Line::Editor&);
bool is_waiting_for(pid_t pid) const { return m_waiting_for_pid == pid; }
String get_history_path(); String get_history_path();
void load_history(); void load_history();
void save_history(); void save_history();
@ -187,6 +189,7 @@ private:
StringBuilder m_complete_line_builder; StringBuilder m_complete_line_builder;
bool m_should_break_current_command { false }; bool m_should_break_current_command { false };
bool m_should_ignore_jobs_on_next_exit { false }; bool m_should_ignore_jobs_on_next_exit { false };
pid_t m_waiting_for_pid { -1 };
}; };
static constexpr bool is_word_character(char c) static constexpr bool is_word_character(char c)

View file

@ -58,7 +58,7 @@ void FileDescriptionCollector::add(int fd)
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
Core::EventLoop loop; Core::EventLoop loop;
signal(SIGINT, [](int) { signal(SIGINT, [](int) {
editor->interrupted(); editor->interrupted();
}); });
@ -74,6 +74,8 @@ int main(int argc, char** argv)
signal(SIGCHLD, [](int) { signal(SIGCHLD, [](int) {
auto& jobs = s_shell->jobs; auto& jobs = s_shell->jobs;
for (auto& job : jobs) { for (auto& job : jobs) {
if (s_shell->is_waiting_for(job.value->pid()))
continue;
int wstatus = 0; int wstatus = 0;
auto child_pid = waitpid(job.value->pid(), &wstatus, WNOHANG); auto child_pid = waitpid(job.value->pid(), &wstatus, WNOHANG);
if (child_pid == job.value->pid()) { if (child_pid == job.value->pid()) {