@@ -531,13 +531,20 @@ At the moment gdbserver is only supported on P8 and P9 and P10.
Memory access can only be performed on kernel memory.
-To run a gdbserver on a P8 machine from a BMC running openbmc:
+To run a gdbserver on a machine from a BMC running OpenBMC:
-Stop all the threads of the core you want to look at
-$ ./pdbg -d p8 -c11 -a stop
+Stop all the threads of the core(s) you want to look at. Ideally all
+threads in the machine should be debugged:
-Run gdbserver on thread 0 of core 11, accessible through port 44
-$ ./pdbg -d p8 -p0 -c11 -t0 gdbserver 44
+$ ./pdbg -a stop
+
+Run gdbserver on the target threads, accessible through port 44
+$ ./pdbg -a gdbserver 44
+
+The thread-id tid is set to the PIR of the corresponding thread, the
+hard_smp_processor_id. Be warned, "info threads" or other gdb operations
+that iterate over all threads may be very slow when debugging a lot
+of threads, especially over slow remote links.
On your local machine:
$ gdb
@@ -111,14 +111,15 @@
# TODO: We don't actually listen to what's supported
q_attached = ('qAttached:' xdigit* @{rsp = "1";});
- q_C = ('qC' @{rsp = "QC1";});
- q_supported = ('qSupported:' any* >{rsp = "multiprocess+;vContSupported+;QStartNoAckMode+"; ack_mode = true;});
- qf_threadinfo = ('qfThreadInfo' @{rsp = "m1l";});
+ q_supported = ('qSupported:' any* >{rsp = "multiprocess+;swbreak+;hwbreak-;qRelocInsn-;vContSupported+;QThreadEvents-;no-resumed-;QStartNoAckMode+"; ack_mode = true;});
q_start_noack = ('QStartNoAckMode' @{rsp = "OK"; send_ack(priv); ack_mode = false;});
# thread info
+ is_alive = ('T' ('p' xdigit+ '.')+ xdigit+ @{rsp = "OK";});
get_thread = ('qC' @{cmd = GET_THREAD;});
set_thread = ('Hg' ('p' xdigit+ '.')+ xdigit+ $hex_digit %push @{cmd = SET_THREAD;});
+ qf_threadinfo = ('qfThreadInfo' @{cmd = QF_THREADINFO;});
+ qs_threadinfo = ('qsThreadInfo' @{cmd = QS_THREADINFO;});
# vCont packet parsing
v_contq = ('vCont?' @{rsp = "vCont;c;C;s;S";});
@@ -128,9 +129,12 @@
interrupt = (3 @{ if (command_callbacks) command_callbacks[INTERRUPT](stack, priv); PR_INFO("RAGEL:interrupt\n");});
- commands = (get_mem | get_gprs | get_spr | stop_reason | get_thread | set_thread |
- q_attached | q_C | q_supported | qf_threadinfo | q_C |
- q_start_noack | v_contq | v_contc | v_conts | put_mem |
+ commands = (get_gprs | get_spr |
+ q_attached | q_supported | q_start_noack |
+ stop_reason | is_alive | get_thread | set_thread |
+ v_contq | v_contc | v_conts |
+ qf_threadinfo | qs_threadinfo |
+ get_mem | put_mem |
detach | unknown );
cmd = (('$' ((commands & ^'#'*) >reset $crc)
@@ -11,7 +11,7 @@
#include "debug.h"
-#line 145 "src/gdb_parser.rl"
+#line 149 "src/gdb_parser.rl"
static enum gdb_command cmd = NONE;
@@ -31,76 +31,86 @@ static bool ack_mode = true;
#line 32 "src/gdb_parser.c"
static const char _gdb_actions[] = {
0, 1, 0, 1, 1, 1, 2, 1,
- 3, 1, 15, 1, 23, 1, 24, 1,
- 25, 1, 26, 2, 0, 1, 2, 2,
+ 3, 1, 14, 1, 24, 1, 25, 1,
+ 26, 1, 27, 2, 0, 1, 2, 2,
1, 2, 3, 1, 2, 3, 5, 2,
- 4, 1, 2, 13, 1, 2, 15, 1,
- 2, 16, 1, 2, 17, 1, 2, 20,
- 1, 2, 21, 1, 2, 22, 1, 3,
- 0, 6, 1, 3, 0, 7, 1, 3,
- 0, 9, 1, 3, 0, 10, 1, 3,
- 0, 11, 1, 3, 0, 12, 1, 3,
- 2, 8, 1, 3, 3, 19, 1, 3,
- 18, 14, 1
+ 4, 1, 2, 13, 1, 2, 14, 1,
+ 2, 15, 1, 2, 16, 1, 2, 17,
+ 1, 2, 19, 1, 2, 20, 1, 2,
+ 21, 1, 2, 22, 1, 2, 23, 1,
+ 3, 0, 6, 1, 3, 0, 7, 1,
+ 3, 0, 9, 1, 3, 0, 10, 1,
+ 3, 0, 11, 1, 3, 0, 12, 1,
+ 3, 2, 8, 1, 3, 3, 18, 1
+
};
-static const unsigned char _gdb_key_offsets[] = {
- 0, 0, 11, 12, 18, 24, 31, 38,
- 40, 42, 49, 57, 65, 72, 79, 87,
- 94, 102, 109, 111, 113, 115, 117, 119,
- 121, 123, 125, 127, 129, 131, 133, 135,
- 137, 144, 152, 157, 159, 161, 163, 165,
- 167, 169, 171, 173, 180, 182, 184, 186,
- 188, 190, 192, 194, 196, 198, 199, 201,
- 203, 205, 207, 209, 211, 213, 215, 217,
- 219, 221, 223, 225, 227, 230, 233, 234,
- 235
+static const short _gdb_key_offsets[] = {
+ 0, 0, 12, 13, 19, 25, 32, 39,
+ 41, 43, 50, 58, 66, 73, 80, 88,
+ 95, 103, 110, 112, 114, 116, 118, 120,
+ 122, 124, 126, 128, 130, 132, 134, 136,
+ 138, 140, 147, 155, 163, 170, 177, 185,
+ 191, 193, 195, 197, 199, 201, 203, 205,
+ 207, 214, 216, 218, 220, 222, 224, 226,
+ 228, 230, 232, 233, 235, 237, 239, 241,
+ 243, 245, 247, 249, 251, 253, 255, 257,
+ 259, 261, 263, 265, 267, 269, 271, 273,
+ 275, 277, 279, 281, 284, 287, 288, 289
};
static const char _gdb_trans_keys[] = {
- 35, 63, 68, 72, 77, 81, 103, 109,
- 112, 113, 118, 35, 48, 57, 65, 70,
- 97, 102, 48, 57, 65, 70, 97, 102,
- 35, 48, 57, 65, 70, 97, 102, 35,
- 48, 57, 65, 70, 97, 102, 35, 103,
- 35, 112, 35, 48, 57, 65, 70, 97,
- 102, 35, 46, 48, 57, 65, 70, 97,
- 102, 35, 112, 48, 57, 65, 70, 97,
+ 35, 63, 68, 72, 77, 81, 84, 103,
+ 109, 112, 113, 118, 35, 48, 57, 65,
+ 70, 97, 102, 48, 57, 65, 70, 97,
102, 35, 48, 57, 65, 70, 97, 102,
35, 48, 57, 65, 70, 97, 102, 35,
- 44, 48, 57, 65, 70, 97, 102, 35,
- 48, 57, 65, 70, 97, 102, 35, 58,
- 48, 57, 65, 70, 97, 102, 35, 48,
- 57, 65, 70, 97, 102, 35, 83, 35,
- 116, 35, 97, 35, 114, 35, 116, 35,
- 78, 35, 111, 35, 65, 35, 99, 35,
- 107, 35, 77, 35, 111, 35, 100, 35,
- 101, 35, 48, 57, 65, 70, 97, 102,
+ 103, 35, 112, 35, 48, 57, 65, 70,
+ 97, 102, 35, 46, 48, 57, 65, 70,
+ 97, 102, 35, 112, 48, 57, 65, 70,
+ 97, 102, 35, 48, 57, 65, 70, 97,
+ 102, 35, 48, 57, 65, 70, 97, 102,
35, 44, 48, 57, 65, 70, 97, 102,
- 35, 65, 67, 83, 102, 35, 116, 35,
- 116, 35, 97, 35, 99, 35, 104, 35,
- 101, 35, 100, 35, 58, 35, 48, 57,
- 65, 70, 97, 102, 35, 117, 35, 112,
- 35, 112, 35, 111, 35, 114, 35, 116,
- 35, 101, 35, 100, 35, 58, 35, 35,
- 84, 35, 104, 35, 114, 35, 101, 35,
- 97, 35, 100, 35, 73, 35, 110, 35,
- 102, 35, 111, 35, 67, 35, 111, 35,
- 110, 35, 116, 35, 59, 63, 35, 99,
- 115, 35, 35, 3, 36, 43, 45, 0
+ 35, 48, 57, 65, 70, 97, 102, 35,
+ 58, 48, 57, 65, 70, 97, 102, 35,
+ 48, 57, 65, 70, 97, 102, 35, 83,
+ 35, 116, 35, 97, 35, 114, 35, 116,
+ 35, 78, 35, 111, 35, 65, 35, 99,
+ 35, 107, 35, 77, 35, 111, 35, 100,
+ 35, 101, 35, 112, 35, 48, 57, 65,
+ 70, 97, 102, 35, 46, 48, 57, 65,
+ 70, 97, 102, 35, 112, 48, 57, 65,
+ 70, 97, 102, 35, 48, 57, 65, 70,
+ 97, 102, 35, 48, 57, 65, 70, 97,
+ 102, 35, 44, 48, 57, 65, 70, 97,
+ 102, 35, 65, 67, 83, 102, 115, 35,
+ 116, 35, 116, 35, 97, 35, 99, 35,
+ 104, 35, 101, 35, 100, 35, 58, 35,
+ 48, 57, 65, 70, 97, 102, 35, 117,
+ 35, 112, 35, 112, 35, 111, 35, 114,
+ 35, 116, 35, 101, 35, 100, 35, 58,
+ 35, 35, 84, 35, 104, 35, 114, 35,
+ 101, 35, 97, 35, 100, 35, 73, 35,
+ 110, 35, 102, 35, 111, 35, 84, 35,
+ 104, 35, 114, 35, 101, 35, 97, 35,
+ 100, 35, 73, 35, 110, 35, 102, 35,
+ 111, 35, 67, 35, 111, 35, 110, 35,
+ 116, 35, 59, 63, 35, 99, 115, 35,
+ 35, 3, 36, 43, 45, 0
};
static const char _gdb_single_lengths[] = {
- 0, 11, 1, 0, 0, 1, 1, 2,
+ 0, 12, 1, 0, 0, 1, 1, 2,
2, 1, 2, 2, 1, 1, 2, 1,
2, 1, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2,
- 1, 2, 5, 2, 2, 2, 2, 2,
- 2, 2, 2, 1, 2, 2, 2, 2,
- 2, 2, 2, 2, 2, 1, 2, 2,
+ 2, 1, 2, 2, 1, 1, 2, 6,
2, 2, 2, 2, 2, 2, 2, 2,
- 2, 2, 2, 2, 3, 3, 1, 1,
- 4
+ 1, 2, 2, 2, 2, 2, 2, 2,
+ 2, 2, 1, 2, 2, 2, 2, 2,
+ 2, 2, 2, 2, 2, 2, 2, 2,
+ 2, 2, 2, 2, 2, 2, 2, 2,
+ 2, 2, 2, 3, 3, 1, 1, 4
};
static const char _gdb_range_lengths[] = {
@@ -108,111 +118,125 @@ static const char _gdb_range_lengths[] = {
0, 3, 3, 3, 3, 3, 3, 3,
3, 3, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0,
- 3, 3, 0, 0, 0, 0, 0, 0,
- 0, 0, 0, 3, 0, 0, 0, 0,
+ 0, 3, 3, 3, 3, 3, 3, 0,
0, 0, 0, 0, 0, 0, 0, 0,
+ 3, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0,
- 0
+ 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0
};
static const short _gdb_index_offsets[] = {
- 0, 0, 12, 14, 18, 22, 27, 32,
- 35, 38, 43, 49, 55, 60, 65, 71,
- 76, 82, 87, 90, 93, 96, 99, 102,
- 105, 108, 111, 114, 117, 120, 123, 126,
- 129, 134, 140, 146, 149, 152, 155, 158,
- 161, 164, 167, 170, 175, 178, 181, 184,
- 187, 190, 193, 196, 199, 202, 204, 207,
- 210, 213, 216, 219, 222, 225, 228, 231,
- 234, 237, 240, 243, 246, 250, 254, 256,
- 258
+ 0, 0, 13, 15, 19, 23, 28, 33,
+ 36, 39, 44, 50, 56, 61, 66, 72,
+ 77, 83, 88, 91, 94, 97, 100, 103,
+ 106, 109, 112, 115, 118, 121, 124, 127,
+ 130, 133, 138, 144, 150, 155, 160, 166,
+ 173, 176, 179, 182, 185, 188, 191, 194,
+ 197, 202, 205, 208, 211, 214, 217, 220,
+ 223, 226, 229, 231, 234, 237, 240, 243,
+ 246, 249, 252, 255, 258, 261, 264, 267,
+ 270, 273, 276, 279, 282, 285, 288, 291,
+ 294, 297, 300, 303, 307, 311, 313, 315
};
static const char _gdb_indicies[] = {
1, 2, 3, 4, 5, 6, 7, 8,
- 9, 10, 11, 0, 13, 12, 14, 14,
- 14, 15, 16, 16, 16, 15, 13, 17,
- 17, 17, 12, 18, 17, 17, 17, 12,
- 13, 19, 12, 13, 20, 12, 13, 21,
- 21, 21, 12, 13, 22, 21, 21, 21,
- 12, 13, 20, 23, 23, 23, 12, 18,
- 23, 23, 23, 12, 13, 24, 24, 24,
- 12, 13, 25, 24, 24, 24, 12, 13,
- 26, 26, 26, 12, 13, 27, 26, 26,
- 26, 12, 13, 28, 28, 28, 12, 13,
- 29, 12, 13, 30, 12, 13, 31, 12,
- 13, 32, 12, 13, 33, 12, 13, 34,
- 12, 13, 35, 12, 13, 36, 12, 13,
- 37, 12, 13, 38, 12, 13, 39, 12,
- 13, 40, 12, 13, 41, 12, 13, 42,
- 12, 13, 43, 43, 43, 12, 13, 44,
- 43, 43, 43, 12, 13, 45, 46, 47,
- 48, 12, 13, 49, 12, 13, 50, 12,
- 13, 51, 12, 13, 52, 12, 13, 53,
- 12, 13, 54, 12, 13, 55, 12, 13,
- 56, 12, 13, 57, 57, 57, 12, 13,
- 58, 12, 13, 59, 12, 13, 60, 12,
- 13, 61, 12, 13, 62, 12, 13, 63,
- 12, 13, 64, 12, 13, 65, 12, 13,
- 66, 12, 68, 67, 13, 69, 12, 13,
- 70, 12, 13, 71, 12, 13, 72, 12,
- 13, 73, 12, 13, 74, 12, 13, 75,
- 12, 13, 76, 12, 13, 77, 12, 13,
- 78, 12, 13, 79, 12, 13, 80, 12,
- 13, 81, 12, 13, 82, 12, 13, 83,
- 84, 12, 13, 85, 86, 12, 13, 87,
- 13, 88, 89, 90, 91, 92, 15, 0
+ 9, 10, 11, 12, 0, 14, 13, 15,
+ 15, 15, 16, 17, 17, 17, 16, 14,
+ 18, 18, 18, 13, 19, 18, 18, 18,
+ 13, 14, 20, 13, 14, 21, 13, 14,
+ 22, 22, 22, 13, 14, 23, 22, 22,
+ 22, 13, 14, 21, 24, 24, 24, 13,
+ 19, 24, 24, 24, 13, 14, 25, 25,
+ 25, 13, 14, 26, 25, 25, 25, 13,
+ 14, 27, 27, 27, 13, 14, 28, 27,
+ 27, 27, 13, 14, 29, 29, 29, 13,
+ 14, 30, 13, 14, 31, 13, 14, 32,
+ 13, 14, 33, 13, 14, 34, 13, 14,
+ 35, 13, 14, 36, 13, 14, 37, 13,
+ 14, 38, 13, 14, 39, 13, 14, 40,
+ 13, 14, 41, 13, 14, 42, 13, 14,
+ 43, 13, 14, 44, 13, 14, 45, 45,
+ 45, 13, 14, 46, 45, 45, 45, 13,
+ 14, 44, 47, 47, 47, 13, 14, 47,
+ 47, 47, 13, 14, 48, 48, 48, 13,
+ 14, 49, 48, 48, 48, 13, 14, 50,
+ 51, 52, 53, 54, 13, 14, 55, 13,
+ 14, 56, 13, 14, 57, 13, 14, 58,
+ 13, 14, 59, 13, 14, 60, 13, 14,
+ 61, 13, 14, 62, 13, 14, 63, 63,
+ 63, 13, 14, 64, 13, 14, 65, 13,
+ 14, 66, 13, 14, 67, 13, 14, 68,
+ 13, 14, 69, 13, 14, 70, 13, 14,
+ 71, 13, 14, 72, 13, 74, 73, 14,
+ 75, 13, 14, 76, 13, 14, 77, 13,
+ 14, 78, 13, 14, 79, 13, 14, 80,
+ 13, 14, 81, 13, 14, 82, 13, 14,
+ 83, 13, 14, 84, 13, 14, 85, 13,
+ 14, 86, 13, 14, 87, 13, 14, 88,
+ 13, 14, 89, 13, 14, 90, 13, 14,
+ 91, 13, 14, 92, 13, 14, 93, 13,
+ 14, 94, 13, 14, 95, 13, 14, 96,
+ 13, 14, 97, 13, 14, 98, 13, 14,
+ 99, 100, 13, 14, 101, 102, 13, 14,
+ 103, 14, 104, 105, 106, 107, 108, 16,
+ 0
};
static const char _gdb_trans_targs[] = {
- 2, 3, 2, 5, 7, 13, 18, 2,
- 32, 5, 34, 64, 2, 3, 4, 0,
- 72, 6, 3, 8, 9, 10, 11, 12,
- 14, 15, 16, 17, 17, 19, 20, 21,
- 22, 23, 24, 25, 26, 27, 28, 29,
- 30, 31, 2, 33, 5, 35, 2, 44,
- 54, 36, 37, 38, 39, 40, 41, 42,
- 43, 43, 45, 46, 47, 48, 49, 50,
- 51, 52, 53, 2, 3, 55, 56, 57,
- 58, 59, 60, 61, 62, 63, 2, 65,
- 66, 67, 68, 69, 2, 70, 71, 70,
- 71, 72, 1, 72, 72
+ 2, 3, 2, 5, 7, 13, 18, 32,
+ 2, 37, 5, 39, 79, 2, 3, 4,
+ 0, 87, 6, 3, 8, 9, 10, 11,
+ 12, 14, 15, 16, 17, 17, 19, 20,
+ 21, 22, 23, 24, 25, 26, 27, 28,
+ 29, 30, 31, 2, 33, 34, 35, 36,
+ 38, 5, 40, 2, 49, 59, 69, 41,
+ 42, 43, 44, 45, 46, 47, 48, 48,
+ 50, 51, 52, 53, 54, 55, 56, 57,
+ 58, 2, 3, 60, 61, 62, 63, 64,
+ 65, 66, 67, 68, 2, 70, 71, 72,
+ 73, 74, 75, 76, 77, 78, 2, 80,
+ 81, 82, 83, 84, 2, 85, 86, 85,
+ 86, 87, 1, 87, 87
};
static const char _gdb_trans_actions[] = {
- 19, 1, 71, 75, 19, 59, 19, 63,
- 55, 67, 19, 19, 3, 0, 7, 0,
- 28, 25, 5, 3, 3, 3, 3, 83,
- 25, 22, 25, 79, 31, 3, 3, 3,
+ 19, 1, 80, 84, 19, 68, 19, 19,
+ 72, 64, 76, 19, 19, 3, 0, 7,
+ 0, 28, 25, 5, 3, 3, 3, 3,
+ 92, 25, 22, 25, 88, 31, 3, 3,
3, 3, 3, 3, 3, 3, 3, 3,
- 3, 3, 43, 25, 22, 3, 87, 3,
+ 3, 3, 3, 40, 3, 3, 3, 43,
+ 25, 22, 3, 46, 3, 3, 3, 3,
+ 3, 3, 3, 3, 3, 3, 3, 34,
3, 3, 3, 3, 3, 3, 3, 3,
- 3, 34, 3, 3, 3, 3, 3, 3,
- 3, 3, 3, 37, 9, 3, 3, 3,
- 3, 3, 3, 3, 3, 3, 40, 3,
- 3, 3, 3, 3, 46, 3, 3, 49,
- 52, 11, 13, 15, 17
+ 3, 37, 9, 3, 3, 3, 3, 3,
+ 3, 3, 3, 3, 49, 3, 3, 3,
+ 3, 3, 3, 3, 3, 3, 52, 3,
+ 3, 3, 3, 3, 55, 3, 3, 58,
+ 61, 11, 13, 15, 17
};
-static const int gdb_start = 72;
-static const int gdb_first_final = 72;
+static const int gdb_start = 87;
+static const int gdb_first_final = 87;
static const int gdb_error = 0;
-static const int gdb_en_main = 72;
+static const int gdb_en_main = 87;
-#line 161 "src/gdb_parser.rl"
+#line 165 "src/gdb_parser.rl"
void parser_init(command_cb *callbacks)
{
-#line 211 "src/gdb_parser.c"
+#line 235 "src/gdb_parser.c"
{
cs = gdb_start;
}
-#line 165 "src/gdb_parser.rl"
+#line 169 "src/gdb_parser.rl"
command_callbacks = callbacks;
}
@@ -223,7 +247,7 @@ int parse_buffer(char *buf, size_t len, void *priv)
char *pe = p + len;
-#line 227 "src/gdb_parser.c"
+#line 251 "src/gdb_parser.c"
{
int _klen;
unsigned int _trans;
@@ -418,57 +442,61 @@ _match:
break;
case 14:
#line 114 "src/gdb_parser.rl"
- {rsp = "QC1";}
+ {rsp = "multiprocess+;swbreak+;hwbreak-;qRelocInsn-;vContSupported+;QThreadEvents-;no-resumed-;QStartNoAckMode+"; ack_mode = true;}
break;
case 15:
#line 115 "src/gdb_parser.rl"
- {rsp = "multiprocess+;vContSupported+;QStartNoAckMode+"; ack_mode = true;}
+ {rsp = "OK"; send_ack(priv); ack_mode = false;}
break;
case 16:
-#line 116 "src/gdb_parser.rl"
- {rsp = "m1l";}
+#line 118 "src/gdb_parser.rl"
+ {rsp = "OK";}
break;
case 17:
-#line 117 "src/gdb_parser.rl"
- {rsp = "OK"; send_ack(priv); ack_mode = false;}
+#line 119 "src/gdb_parser.rl"
+ {cmd = GET_THREAD;}
break;
case 18:
#line 120 "src/gdb_parser.rl"
- {cmd = GET_THREAD;}
+ {cmd = SET_THREAD;}
break;
case 19:
#line 121 "src/gdb_parser.rl"
- {cmd = SET_THREAD;}
+ {cmd = QF_THREADINFO;}
break;
case 20:
-#line 124 "src/gdb_parser.rl"
- {rsp = "vCont;c;C;s;S";}
+#line 122 "src/gdb_parser.rl"
+ {cmd = QS_THREADINFO;}
break;
case 21:
#line 125 "src/gdb_parser.rl"
- {cmd = V_CONTC;}
+ {rsp = "vCont;c;C;s;S";}
break;
case 22:
#line 126 "src/gdb_parser.rl"
- {cmd = V_CONTS;}
+ {cmd = V_CONTC;}
break;
case 23:
-#line 129 "src/gdb_parser.rl"
- { if (command_callbacks) command_callbacks[INTERRUPT](stack, priv); PR_INFO("RAGEL:interrupt\n");}
+#line 127 "src/gdb_parser.rl"
+ {cmd = V_CONTS;}
break;
case 24:
-#line 137 "src/gdb_parser.rl"
- {PR_INFO("RAGEL:cmd\n");}
+#line 130 "src/gdb_parser.rl"
+ { if (command_callbacks) command_callbacks[INTERRUPT](stack, priv); PR_INFO("RAGEL:interrupt\n");}
break;
case 25:
-#line 140 "src/gdb_parser.rl"
- {PR_INFO("RAGEL:ack\n");}
+#line 141 "src/gdb_parser.rl"
+ {PR_INFO("RAGEL:cmd\n");}
break;
case 26:
-#line 141 "src/gdb_parser.rl"
+#line 144 "src/gdb_parser.rl"
+ {PR_INFO("RAGEL:ack\n");}
+ break;
+ case 27:
+#line 145 "src/gdb_parser.rl"
{PR_INFO("RAGEL:nack\n");}
break;
-#line 472 "src/gdb_parser.c"
+#line 500 "src/gdb_parser.c"
}
}
@@ -481,7 +509,7 @@ _again:
_out: {}
}
-#line 175 "src/gdb_parser.rl"
+#line 179 "src/gdb_parser.rl"
if (cs == gdb_error) {
printf("parse error\n");
@@ -142,6 +142,58 @@ static void set_thread(uint64_t *stack, void *priv)
send_response(fd, ERROR(EEXIST));
}
+static int threadinfo_iterator;
+
+static void qs_threadinfo(uint64_t *stack, void *priv)
+{
+ struct pdbg_target *target;
+ char data[MAX_RESP_LEN] = "m";
+ size_t s = 1;
+ int iter = 0;
+ bool found = false;
+
+ for_each_path_target_class("thread", target) {
+ struct thread *thread = target_to_thread(target);
+ struct gdb_thread *gdb_thread = thread->gdbserver_priv;
+
+ if (pdbg_target_status(target) != PDBG_TARGET_ENABLED)
+ continue;
+
+ if (!found && iter < threadinfo_iterator) {
+ iter++;
+ continue;
+ }
+
+ found = true;
+
+ if (iter == threadinfo_iterator)
+ s += snprintf(data + s, sizeof(data) - s,
+ "%04" PRIx64, gdb_thread->pir);
+ else
+ s += snprintf(data + s, sizeof(data) - s,
+ ",%04" PRIx64, gdb_thread->pir);
+ threadinfo_iterator++;
+
+ if (sizeof(data) - s < 9) /* comma, 7 digits, NUL */
+ break;
+
+ }
+
+ PR_INFO("qf_threadinfo %s\n", data);
+
+ if (s > 1)
+ send_response(fd, data);
+ else
+ send_response(fd, "l");
+}
+
+static void qf_threadinfo(uint64_t *stack, void *priv)
+{
+ threadinfo_iterator = 0;
+
+ qs_threadinfo(stack, priv);
+}
+
static void send_stop_for_thread(struct pdbg_target *target)
{
struct thread *thread = target_to_thread(target);
@@ -880,12 +932,14 @@ static command_cb callbacks[LAST_CMD + 1] = {
cmd_default,
get_gprs,
get_spr,
- get_mem,
stop_reason,
get_thread,
set_thread,
v_contc,
v_conts,
+ qf_threadinfo,
+ qs_threadinfo,
+ get_mem,
put_mem,
interrupt,
detach,
@@ -1018,12 +1072,8 @@ static int gdbserver(uint16_t port)
memset(gdb_thread, 0, sizeof(*gdb_thread));
thread->gdbserver_priv = gdb_thread;
- if (!first_target) {
+ if (!first_target)
first_target = target;
- } else {
- fprintf(stderr, "GDB server cannot be run on multiple threads at once.\n");
- return 0;
- }
}
if (!first_target) {
@@ -1039,6 +1089,10 @@ static int gdbserver(uint16_t port)
PR_WARNING("Breakpoints may cause host crashes on POWER9 and should not be used\n");
}
+ if (!path_target_all_selected("thread", NULL)) {
+ PR_WARNING("GDBSERVER works best when targeting all threads (-a)\n");
+ }
+
thread_target = first_target;
for_each_path_target_class("thread", target) {
@@ -1,9 +1,13 @@
#ifndef __PDBGPROXY_H
#define __PDBGPROXY_H
-enum gdb_command {NONE, GET_GPRS, GET_SPR, GET_MEM,
- STOP_REASON, GET_THREAD, SET_THREAD, V_CONTC, V_CONTS,
- PUT_MEM, INTERRUPT, DETACH, LAST_CMD};
+enum gdb_command {NONE, GET_GPRS, GET_SPR,
+ STOP_REASON, GET_THREAD, SET_THREAD,
+ V_CONTC, V_CONTS,
+ QF_THREADINFO, QS_THREADINFO,
+ GET_MEM, PUT_MEM,
+ INTERRUPT, DETACH, LAST_CMD};
+
typedef void (*command_cb)(uint64_t *stack, void *priv);
void parser_init(command_cb *callbacks);
This implements the threadinfo gdb commands, and removes the restriction of a single target. Signed-off-by: Nicholas Piggin <npiggin@gmail.com> --- README.md | 17 +- src/gdb_parser.rl | 16 +- src/gdb_parser_precompile.c | 328 +++++++++++++++++++----------------- src/pdbgproxy.c | 66 +++++++- src/pdbgproxy.h | 10 +- 5 files changed, 267 insertions(+), 170 deletions(-)