Use the new input_common_add_callback mechanism to not execute callbacks while signals are blocked. Should fix https://github.com/fish-shell/fish-shell/issues/608

This commit is contained in:
ridiculousfish 2013-04-03 17:26:02 -07:00
parent 1543d02f96
commit d9445f04b1
4 changed files with 22 additions and 6 deletions

View File

@ -19,6 +19,7 @@
#include "wutil.h" #include "wutil.h"
#include "function.h" #include "function.h"
#include "input_common.h"
#include "proc.h" #include "proc.h"
#include "parser.h" #include "parser.h"
#include "common.h" #include "common.h"
@ -441,6 +442,16 @@ static int event_is_killed(const event_t &e)
return std::find(killme.begin(), killme.end(), &e) != killme.end(); return std::find(killme.begin(), killme.end(), &e) != killme.end();
} }
/* Callback for firing (and then deleting) an event */
static void fire_event_callback(void *arg)
{
ASSERT_IS_MAIN_THREAD();
assert(arg != NULL);
event_t *event = static_cast<event_t *>(arg);
event_fire(event);
delete event;
}
/** /**
Perform the specified event. Since almost all event firings will Perform the specified event. Since almost all event firings will
not be matched by even a single event handler, we make sure to not be matched by even a single event handler, we make sure to
@ -488,6 +499,14 @@ static void event_fire_internal(const event_t &event)
if (fire.empty()) if (fire.empty())
return; return;
if (signal_is_blocked())
{
/* Fix for https://github.com/fish-shell/fish-shell/issues/608. Don't run event handlers while signals are blocked. */
event_t *heap_event = new event_t(event);
input_common_add_callback(fire_event_callback, heap_event);
return;
}
/* /*
Iterate over our list of matching events Iterate over our list of matching events
*/ */
@ -637,10 +656,10 @@ void event_fire_signal(int signal)
} }
void event_fire(event_t *event) void event_fire(const event_t *event)
{ {
if (event && (event->type == EVENT_SIGNAL)) if (event && event->type == EVENT_SIGNAL)
{ {
event_fire_signal(event->param1.signal); event_fire_signal(event->param1.signal);
} }

View File

@ -144,7 +144,7 @@ bool event_is_signal_observed(int signal);
\param event the specific event whose handlers should fire. If \param event the specific event whose handlers should fire. If
null, then all delayed events will be fired. null, then all delayed events will be fired.
*/ */
void event_fire(event_t *event); void event_fire(const event_t *event);
/** Like event_fire, but takes a signal directly. */ /** Like event_fire, but takes a signal directly. */
void event_fire_signal(int signal); void event_fire_signal(int signal);

View File

@ -128,7 +128,6 @@ bool input_terminfo_get_name(const wcstring &seq, wcstring &name);
/** Return a list of all known terminfo names */ /** Return a list of all known terminfo names */
wcstring_list_t input_terminfo_get_names(bool skip_null); wcstring_list_t input_terminfo_get_names(bool skip_null);
/** Returns the input function code for the given input function name. */ /** Returns the input function code for the given input function name. */
wchar_t input_function_get_code(const wcstring &name); wchar_t input_function_get_code(const wcstring &name);

View File

@ -56,6 +56,4 @@ void input_common_unreadch(wint_t ch);
/** Adds a callback to be invoked at the next turn of the "event loop." The callback function will be invoked and passed arg. */ /** Adds a callback to be invoked at the next turn of the "event loop." The callback function will be invoked and passed arg. */
void input_common_add_callback(void (*callback)(void *), void *arg); void input_common_add_callback(void (*callback)(void *), void *arg);
#endif #endif