X-Git-Url: http://git.efficios.com/?a=blobdiff_plain;f=gdbserver%2Fserver.cc;h=0313d18bb24720c2f8c07046715f19a988540f8e;hb=refs%2Fheads%2Fconcurrent-displaced-stepping-2020-04-01;hp=670c0fed968c1f56296d8d09ccf391f950792990;hpb=29e8dc09ff78e102ede0cdbb802cb771613bb8b1;p=deliverable%2Fbinutils-gdb.git diff --git a/gdbserver/server.cc b/gdbserver/server.cc index 670c0fed96..0313d18bb2 100644 --- a/gdbserver/server.cc +++ b/gdbserver/server.cc @@ -47,6 +47,7 @@ #include "gdbsupport/selftest.h" #include "gdbsupport/scope-exit.h" +#include "gdbsupport/gdb_select.h" #define require_running_or_return(BUF) \ if (!target_running ()) \ @@ -82,6 +83,10 @@ bool run_once; /* Whether to report TARGET_WAITKIND_NO_RESUMED events. */ static bool report_no_resumed; +/* The event loop checks this to decide whether to continue accepting + events. */ +static bool keep_processing_events = true; + bool non_stop; static struct { @@ -130,6 +135,7 @@ bool disable_packet_vCont; bool disable_packet_Tthread; bool disable_packet_qC; bool disable_packet_qfThreadInfo; +bool disable_packet_T; static unsigned char *mem_buf; @@ -740,7 +746,7 @@ handle_general_set (char *own_buf) } req_str = req ? "non-stop" : "all-stop"; - if (the_target->pt->start_non_stop (req == 1) != 0) + if (the_target->start_non_stop (req == 1) != 0) { fprintf (stderr, "Setting %s mode failed\n", req_str); write_enn (own_buf); @@ -1097,7 +1103,7 @@ handle_search_memory_1 (CORE_ADDR start_addr, CORE_ADDR search_space_len, : chunk_size); if (gdb_read_memory (read_addr, search_buf + keep_len, - nr_to_read) != search_buf_size) + nr_to_read) != nr_to_read) { warning ("Unable to access %ld bytes of target memory " "at 0x%lx, halting search.", @@ -1234,7 +1240,7 @@ handle_detach (char *own_buf) debug_printf ("Forcing non-stop mode\n"); non_stop = true; - the_target->pt->start_non_stop (true); + the_target->start_non_stop (true); } process->gdb_detached = 1; @@ -1442,13 +1448,13 @@ handle_qxfer_auxv (const char *annex, gdb_byte *readbuf, const gdb_byte *writebuf, ULONGEST offset, LONGEST len) { - if (!the_target->pt->supports_read_auxv () || writebuf != NULL) + if (!the_target->supports_read_auxv () || writebuf != NULL) return -2; if (annex[0] != '\0' || current_thread == NULL) return -1; - return the_target->pt->read_auxv (offset, readbuf, len); + return the_target->read_auxv (offset, readbuf, len); } /* Handle qXfer:exec-file:read. */ @@ -1462,7 +1468,7 @@ handle_qxfer_exec_file (const char *annex, ULONGEST pid; int total_len; - if (the_target->pid_to_exec_file == NULL || writebuf != NULL) + if (!the_target->supports_pid_to_exec_file () || writebuf != NULL) return -2; if (annex[0] == '\0') @@ -1482,7 +1488,7 @@ handle_qxfer_exec_file (const char *annex, if (pid <= 0) return -1; - file = (*the_target->pid_to_exec_file) (pid); + file = the_target->pid_to_exec_file (pid); if (file == NULL) return -1; @@ -1574,10 +1580,12 @@ handle_qxfer_libraries_svr4 (const char *annex, if (writebuf != NULL) return -2; - if (current_thread == NULL || the_target->qxfer_libraries_svr4 == NULL) + if (current_thread == NULL + || !the_target->supports_qxfer_libraries_svr4 ()) return -1; - return the_target->qxfer_libraries_svr4 (annex, readbuf, writebuf, offset, len); + return the_target->qxfer_libraries_svr4 (annex, readbuf, writebuf, + offset, len); } /* Handle qXfer:osadata:read. */ @@ -1587,10 +1595,10 @@ handle_qxfer_osdata (const char *annex, gdb_byte *readbuf, const gdb_byte *writebuf, ULONGEST offset, LONGEST len) { - if (!the_target->pt->supports_qxfer_osdata () || writebuf != NULL) + if (!the_target->supports_qxfer_osdata () || writebuf != NULL) return -2; - return the_target->pt->qxfer_osdata (annex, readbuf, NULL, offset, len); + return the_target->qxfer_osdata (annex, readbuf, NULL, offset, len); } /* Handle qXfer:siginfo:read and qXfer:siginfo:write. */ @@ -1600,13 +1608,13 @@ handle_qxfer_siginfo (const char *annex, gdb_byte *readbuf, const gdb_byte *writebuf, ULONGEST offset, LONGEST len) { - if (!the_target->pt->supports_qxfer_siginfo ()) + if (!the_target->supports_qxfer_siginfo ()) return -2; if (annex[0] != '\0' || current_thread == NULL) return -1; - return the_target->pt->qxfer_siginfo (annex, readbuf, writebuf, offset, len); + return the_target->qxfer_siginfo (annex, readbuf, writebuf, offset, len); } /* Handle qXfer:statictrace:read. */ @@ -1792,13 +1800,13 @@ static int handle_qxfer_fdpic (const char *annex, gdb_byte *readbuf, const gdb_byte *writebuf, ULONGEST offset, LONGEST len) { - if (!the_target->pt->supports_read_loadmap ()) + if (!the_target->supports_read_loadmap ()) return -2; if (current_thread == NULL) return -1; - return the_target->pt->read_loadmap (annex, offset, readbuf, len); + return the_target->read_loadmap (annex, offset, readbuf, len); } /* Handle qXfer:btrace:read. */ @@ -2193,7 +2201,7 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) tracepoint_look_up_symbols (); if (current_thread != NULL) - the_target->pt->look_up_symbols (); + the_target->look_up_symbols (); current_thread = save_thread; @@ -2234,13 +2242,13 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) } } - if (the_target->pt->supports_read_offsets () + if (the_target->supports_read_offsets () && strcmp ("qOffsets", own_buf) == 0) { CORE_ADDR text, data; require_running_or_return (own_buf); - if (the_target->pt->read_offsets (&text, &data)) + if (the_target->read_offsets (&text, &data)) sprintf (own_buf, "Text=%lX;Data=%lX;Bss=%lX", (long)text, (long)data, (long)data); else @@ -2364,7 +2372,7 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) if (target_supports_catch_syscall ()) strcat (own_buf, ";QCatchSyscalls+"); - if (the_target->qxfer_libraries_svr4 != NULL) + if (the_target->supports_qxfer_libraries_svr4 ()) strcat (own_buf, ";qXfer:libraries-svr4:read+" ";augmented-libraries-svr4-read+"); else @@ -2374,13 +2382,13 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) strcat (own_buf, ";qXfer:libraries:read+"); } - if (the_target->pt->supports_read_auxv ()) + if (the_target->supports_read_auxv ()) strcat (own_buf, ";qXfer:auxv:read+"); - if (the_target->pt->supports_qxfer_siginfo ()) + if (the_target->supports_qxfer_siginfo ()) strcat (own_buf, ";qXfer:siginfo:read+;qXfer:siginfo:write+"); - if (the_target->pt->supports_read_loadmap ()) + if (the_target->supports_read_loadmap ()) strcat (own_buf, ";qXfer:fdpic:read+"); /* We always report qXfer:features:read, as targets may @@ -2392,7 +2400,7 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) if (cs.transport_is_reliable) strcat (own_buf, ";QStartNoAckMode+"); - if (the_target->pt->supports_qxfer_osdata ()) + if (the_target->supports_qxfer_osdata ()) strcat (own_buf, ";qXfer:osdata:read+"); if (target_supports_multi_process ()) @@ -2450,7 +2458,7 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) if (target_supports_stopped_by_hw_breakpoint ()) strcat (own_buf, ";hwbreak+"); - if (the_target->pid_to_exec_file != NULL) + if (the_target->supports_pid_to_exec_file ()) strcat (own_buf, ";qXfer:exec-file:read+"); strcat (own_buf, ";vContSupported+"); @@ -2467,7 +2475,7 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) } /* Thread-local storage support. */ - if (the_target->pt->supports_get_tls_address () + if (the_target->supports_get_tls_address () && startswith (own_buf, "qGetTLSAddr:")) { char *p = own_buf + 12; @@ -2513,8 +2521,8 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) if (thread == NULL) err = 2; else - err = the_target->pt->get_tls_address (thread, parts[0], parts[1], - &address); + err = the_target->get_tls_address (thread, parts[0], parts[1], + &address); } if (err == 0) @@ -2532,7 +2540,7 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) } /* Windows OS Thread Information Block address support. */ - if (the_target->pt->supports_get_tib_address () + if (the_target->supports_get_tib_address () && startswith (own_buf, "qGetTIBAddr:")) { const char *annex; @@ -2540,7 +2548,7 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) CORE_ADDR tlb; ptid_t ptid = read_ptid (own_buf + 12, &annex); - n = the_target->pt->get_tib_address (ptid, &tlb); + n = the_target->get_tib_address (ptid, &tlb); if (n == 1) { strcpy (own_buf, paddress(tlb)); @@ -2577,7 +2585,7 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p) write_ok (own_buf); - if (the_target->pt->handle_monitor_command (mon) == 0) + if (the_target->handle_monitor_command (mon) == 0) /* Default processing. */ handle_monitor_command (mon, own_buf); @@ -2846,7 +2854,7 @@ resume (struct thread_resume *actions, size_t num_actions) enable_async_io (); } - the_target->pt->resume (actions, num_actions); + the_target->resume (actions, num_actions); if (non_stop) write_ok (cs.own_buf); @@ -2949,7 +2957,7 @@ handle_v_run (char *own_buf) else if (p == next_p) { /* Empty argument. */ - new_argv.push_back (xstrdup ("''")); + new_argv.push_back (xstrdup ("")); } else { @@ -3007,7 +3015,6 @@ handle_v_run (char *own_buf) if (*next_p) next_p++; } - new_argv.push_back (NULL); if (new_program_name == NULL) { @@ -3087,7 +3094,7 @@ handle_v_requests (char *own_buf, int packet_len, int *new_packet_len) { if (strcmp (own_buf, "vCtrlC") == 0) { - the_target->pt->request_interrupt (); + the_target->request_interrupt (); write_ok (own_buf); return; } @@ -3217,7 +3224,7 @@ queue_stop_reply_callback (thread_info *thread) { /* For now, assume targets that don't have this callback also don't manage the thread's last_status field. */ - if (!the_target->pt->supports_thread_stopped ()) + if (!the_target->supports_thread_stopped ()) { struct vstop_notif *new_notif = new struct vstop_notif; @@ -3324,7 +3331,7 @@ handle_status (char *own_buf) thread_info *thread = NULL; target_pause_all (false); - stabilize_threads (); + target_stabilize_threads (); gdb_wants_all_threads_stopped (); /* We can only report one status, but we might be coming out of @@ -3459,6 +3466,32 @@ gdbserver_show_disableable (FILE *stream) " threads \tAll of the above\n"); } +/* Start up the event loop. This is the entry point to the event + loop. */ + +static void +start_event_loop () +{ + /* Loop until there is nothing to do. This is the entry point to + the event loop engine. If nothing is ready at this time, wait + for something to happen (via wait_for_event), then process it. + Return when there are no longer event sources to wait for. */ + + keep_processing_events = true; + while (keep_processing_events) + { + /* Any events already waiting in the queue? */ + int res = gdb_do_one_event (); + + /* Was there an error? */ + if (res == -1) + break; + } + + /* We are done with the event loop. There are no more event sources + to listen to. So we exit gdbserver. */ +} + static void kill_inferior_callback (process_info *process) { @@ -3647,6 +3680,8 @@ captured_main (int argc, char *argv[]) disable_packet_qC = true; else if (strcmp ("qfThreadInfo", tok) == 0) disable_packet_qfThreadInfo = true; + else if (strcmp ("T", tok) == 0) + disable_packet_T = true; else if (strcmp ("threads", tok) == 0) { disable_packet_vCont = true; @@ -3756,7 +3791,6 @@ captured_main (int argc, char *argv[]) initialize_async_io (); initialize_low (); have_job_control (); - initialize_event_loop (); if (target_supports_tracepoints ()) initialize_tracepoint (); @@ -3780,7 +3814,6 @@ captured_main (int argc, char *argv[]) program_path.set (make_unique_xstrdup (next_arg[0])); for (i = 1; i < n; i++) program_args.push_back (xstrdup (next_arg[i])); - program_args.push_back (NULL); /* Wait till we are at first instruction in program. */ target_create_inferior (program_path.get (), program_args); @@ -3884,7 +3917,7 @@ captured_main (int argc, char *argv[]) down without informing GDB. */ if (!non_stop) { - if (the_target->pt->start_non_stop (true)) + if (the_target->start_non_stop (true)) non_stop = 1; /* Detaching implicitly resumes all threads; @@ -4359,7 +4392,7 @@ process_serial_event (void) /* Event-loop callback for serial events. */ -int +void handle_serial_event (int err, gdb_client_data client_data) { if (debug_threads) @@ -4367,13 +4400,14 @@ handle_serial_event (int err, gdb_client_data client_data) /* Really handle it. */ if (process_serial_event () < 0) - return -1; + { + keep_processing_events = false; + return; + } /* Be sure to not change the selected thread behind GDB's back. Important in the non-stop mode asynchronous protocol. */ set_desired_thread (); - - return 0; } /* Push a stop notification on the notification queue. */ @@ -4391,7 +4425,7 @@ push_stop_notification (ptid_t ptid, struct target_waitstatus *status) /* Event-loop callback for target events. */ -int +void handle_target_event (int err, gdb_client_data client_data) { client_state &cs = get_client_state (); @@ -4468,10 +4502,42 @@ handle_target_event (int err, gdb_client_data client_data) /* Be sure to not change the selected thread behind GDB's back. Important in the non-stop mode asynchronous protocol. */ set_desired_thread (); +} + +/* See gdbsupport/event-loop.h. */ +int +invoke_async_signal_handlers () +{ + return 0; +} + +/* See gdbsupport/event-loop.h. */ + +int +check_async_event_handlers () +{ return 0; } +/* See gdbsupport/errors.h */ + +void +flush_streams () +{ + fflush (stdout); + fflush (stderr); +} + +/* See gdbsupport/gdb_select.h. */ + +int +gdb_select (int n, fd_set *readfds, fd_set *writefds, + fd_set *exceptfds, struct timeval *timeout) +{ + return select (n, readfds, writefds, exceptfds, timeout); +} + #if GDB_SELF_TEST namespace selftests {