Skip to content

Commit 677d350

Browse files
committed
debugger: get into the debugger on SIGINT
Signed-off-by: Balazs Scheidler <balazs.scheidler@axoflow.com>
1 parent 45672ea commit 677d350

File tree

1 file changed

+49
-13
lines changed

1 file changed

+49
-13
lines changed

lib/debugger/debugger.c

+49-13
Original file line numberDiff line numberDiff line change
@@ -31,12 +31,14 @@
3131
#include "compat/time.h"
3232
#include "scratch-buffers.h"
3333

34+
#include <iv_signal.h>
3435
#include <stdio.h>
3536
#include <unistd.h>
3637

3738
struct _Debugger
3839
{
3940
Tracer *tracer;
41+
struct iv_signal sigint;
4042
MainLoop *main_loop;
4143
GlobalConfig *cfg;
4244
gchar *command_buffer;
@@ -210,7 +212,8 @@ static gboolean
210212
_cmd_quit(Debugger *self, gint argc, gchar *argv[])
211213
{
212214
main_loop_exit(self->main_loop);
213-
self->breakpoint_site->drop = TRUE;
215+
if (self->breakpoint_site)
216+
self->breakpoint_site->drop = TRUE;
214217
return FALSE;
215218
}
216219

@@ -245,22 +248,23 @@ struct
245248
{
246249
const gchar *name;
247250
DebuggerCommandFunc command;
251+
gboolean requires_breakpoint_site;
248252
} command_table[] =
249253
{
250254
{ "help", _cmd_help },
251255
{ "h", _cmd_help },
252256
{ "?", _cmd_help },
253257
{ "continue", _cmd_continue },
254258
{ "c", _cmd_continue },
255-
{ "print", _cmd_print },
256-
{ "p", _cmd_print },
259+
{ "print", _cmd_print, .requires_breakpoint_site = TRUE },
260+
{ "p", _cmd_print, .requires_breakpoint_site = TRUE },
257261
{ "display", _cmd_display },
258-
{ "drop", _cmd_drop },
262+
{ "drop", _cmd_drop, .requires_breakpoint_site = TRUE },
259263
{ "quit", _cmd_quit },
260264
{ "q", _cmd_quit },
261-
{ "trace", _cmd_trace },
262-
{ "info", _cmd_info },
263-
{ "i", _cmd_info },
265+
{ "trace", _cmd_trace, .requires_breakpoint_site = TRUE },
266+
{ "info", _cmd_info, .requires_breakpoint_site = TRUE },
267+
{ "i", _cmd_info, .requires_breakpoint_site = TRUE },
264268
{ NULL, NULL }
265269
};
266270

@@ -319,6 +323,7 @@ _handle_command(Debugger *self)
319323
gint argc;
320324
gchar **argv;
321325
GError *error = NULL;
326+
gboolean requires_breakpoint_site = TRUE;
322327
DebuggerCommandFunc command = NULL;
323328

324329
if (!g_shell_parse_argv(self->command_buffer ? : "", &argc, &argv, &error))
@@ -333,6 +338,7 @@ _handle_command(Debugger *self)
333338
if (strcmp(command_table[i].name, argv[0]) == 0)
334339
{
335340
command = command_table[i].command;
341+
requires_breakpoint_site = command_table[i].requires_breakpoint_site;
336342
break;
337343
}
338344
}
@@ -341,6 +347,11 @@ _handle_command(Debugger *self)
341347
printf("Undefined command %s, try \"help\"\n", argv[0]);
342348
return TRUE;
343349
}
350+
else if (requires_breakpoint_site && self->breakpoint_site == NULL)
351+
{
352+
printf("Running in interrupt context, command %s requires pipeline context\n", argv[0]);
353+
return TRUE;
354+
}
344355
gboolean result = command(self, argc, argv);
345356
g_strfreev(argv);
346357
return result;
@@ -350,11 +361,20 @@ static void
350361
_handle_interactive_prompt(Debugger *self)
351362
{
352363
gchar buf[1024];
353-
LogPipe *current_pipe = self->breakpoint_site->pipe;
364+
LogPipe *current_pipe;
354365

355-
printf("Breakpoint hit %s\n", log_expr_node_format_location(current_pipe->expr_node, buf, sizeof(buf)));
356-
_display_source_line(current_pipe->expr_node);
357-
_display_msg_with_template(self, self->breakpoint_site->msg, self->display_template);
366+
if (self->breakpoint_site)
367+
{
368+
current_pipe = self->breakpoint_site->pipe;
369+
370+
printf("Breakpoint hit %s\n", log_expr_node_format_location(current_pipe->expr_node, buf, sizeof(buf)));
371+
_display_source_line(current_pipe->expr_node);
372+
_display_msg_with_template(self, self->breakpoint_site->msg, self->display_template);
373+
}
374+
else
375+
{
376+
printf("Stopping on interrupt, message related commands are unavailable...\n");
377+
}
358378
while (1)
359379
{
360380
_fetch_command(self);
@@ -374,22 +394,37 @@ _debugger_thread_func(Debugger *self)
374394
while (1)
375395
{
376396
self->breakpoint_site = NULL;
377-
if (!tracer_wait_for_breakpoint(self->tracer, &self->breakpoint_site))
397+
if (!tracer_wait_for_event(self->tracer, &self->breakpoint_site))
378398
break;
379399

380400
_handle_interactive_prompt(self);
381-
tracer_resume_after_breakpoint(self->tracer, self->breakpoint_site);
401+
tracer_resume_after_event(self->tracer, self->breakpoint_site);
382402
}
383403
scratch_buffers_explicit_gc();
384404
app_thread_stop();
385405
return NULL;
386406
}
387407

408+
static void
409+
_interrupt(gpointer user_data)
410+
{
411+
Debugger *self = (Debugger *) user_data;
412+
413+
tracer_stop_on_interrupt(self->tracer);
414+
}
415+
388416
void
389417
debugger_start_console(Debugger *self)
390418
{
391419
main_loop_assert_main_thread();
392420

421+
IV_SIGNAL_INIT(&self->sigint);
422+
self->sigint.signum = SIGINT;
423+
self->sigint.flags = IV_SIGNAL_FLAG_EXCLUSIVE;
424+
self->sigint.cookie = self;
425+
self->sigint.handler = _interrupt;
426+
iv_signal_register(&self->sigint);
427+
393428
self->debugger_thread = g_thread_new(NULL, (GThreadFunc) _debugger_thread_func, self);
394429
}
395430

@@ -429,6 +464,7 @@ debugger_exit(Debugger *self)
429464
{
430465
main_loop_assert_main_thread();
431466

467+
iv_signal_unregister(&self->sigint);
432468
tracer_cancel(self->tracer);
433469
g_thread_join(self->debugger_thread);
434470
}

0 commit comments

Comments
 (0)