OLD | NEW |
1 /* Tracepoint code for remote server for GDB. | 1 /* Tracepoint code for remote server for GDB. |
2 Copyright (C) 2009-2012 Free Software Foundation, Inc. | 2 Copyright (C) 2009-2012 Free Software Foundation, Inc. |
3 | 3 |
4 This file is part of GDB. | 4 This file is part of GDB. |
5 | 5 |
6 This program is free software; you can redistribute it and/or modify | 6 This program is free software; you can redistribute it and/or modify |
7 it under the terms of the GNU General Public License as published by | 7 it under the terms of the GNU General Public License as published by |
8 the Free Software Foundation; either version 3 of the License, or | 8 the Free Software Foundation; either version 3 of the License, or |
9 (at your option) any later version. | 9 (at your option) any later version. |
10 | 10 |
11 This program is distributed in the hope that it will be useful, | 11 This program is distributed in the hope that it will be useful, |
12 but WITHOUT ANY WARRANTY; without even the implied warranty of | 12 but WITHOUT ANY WARRANTY; without even the implied warranty of |
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | 13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
14 GNU General Public License for more details. | 14 GNU General Public License for more details. |
15 | 15 |
16 You should have received a copy of the GNU General Public License | 16 You should have received a copy of the GNU General Public License |
17 along with this program. If not, see <http://www.gnu.org/licenses/>. */ | 17 along with this program. If not, see <http://www.gnu.org/licenses/>. */ |
18 | 18 |
19 #include "server.h" | 19 #include "server.h" |
| 20 #include "gdbthread.h" |
| 21 #include "agent.h" |
| 22 |
20 #include <ctype.h> | 23 #include <ctype.h> |
21 #include <fcntl.h> | 24 #include <fcntl.h> |
22 #include <unistd.h> | 25 #include <unistd.h> |
23 #include <sys/time.h> | 26 #include <sys/time.h> |
24 #include <stddef.h> | 27 #include <stddef.h> |
25 #if HAVE_STDINT_H | 28 #include <inttypes.h> |
26 #include <stdint.h> | 29 #include <stdint.h> |
27 #endif | 30 |
| 31 #include "ax.h" |
28 | 32 |
29 /* This file is built for both GDBserver, and the in-process | 33 /* This file is built for both GDBserver, and the in-process |
30 agent (IPA), a shared library that includes a tracing agent that is | 34 agent (IPA), a shared library that includes a tracing agent that is |
31 loaded by the inferior to support fast tracepoints. Fast | 35 loaded by the inferior to support fast tracepoints. Fast |
32 tracepoints (or more accurately, jump based tracepoints) are | 36 tracepoints (or more accurately, jump based tracepoints) are |
33 implemented by patching the tracepoint location with a jump into a | 37 implemented by patching the tracepoint location with a jump into a |
34 small trampoline function whose job is to save the register state, | 38 small trampoline function whose job is to save the register state, |
35 call the in-process tracing agent, and then execute the original | 39 call the in-process tracing agent, and then execute the original |
36 instruction that was under the tracepoint jump (possibly adjusted, | 40 instruction that was under the tracepoint jump (possibly adjusted, |
37 if PC-relative, or some such). | 41 if PC-relative, or some such). |
(...skipping 18 matching lines...) Expand all Loading... |
56 static void trace_vdebug (const char *, ...) ATTR_FORMAT (printf, 1, 2); | 60 static void trace_vdebug (const char *, ...) ATTR_FORMAT (printf, 1, 2); |
57 | 61 |
58 static void | 62 static void |
59 trace_vdebug (const char *fmt, ...) | 63 trace_vdebug (const char *fmt, ...) |
60 { | 64 { |
61 char buf[1024]; | 65 char buf[1024]; |
62 va_list ap; | 66 va_list ap; |
63 | 67 |
64 va_start (ap, fmt); | 68 va_start (ap, fmt); |
65 vsprintf (buf, fmt, ap); | 69 vsprintf (buf, fmt, ap); |
66 fprintf (stderr, "gdbserver/tracepoint: %s\n", buf); | 70 fprintf (stderr, PROG "/tracepoint: %s\n", buf); |
67 va_end (ap); | 71 va_end (ap); |
68 } | 72 } |
69 | 73 |
70 #define trace_debug_1(level, fmt, args...) \ | 74 #define trace_debug_1(level, fmt, args...) \ |
71 do { \ | 75 do { \ |
72 if (level <= debug_threads)»» » \ | 76 if (level <= debug_threads)»» \ |
73 trace_vdebug ((fmt), ##args); \ | 77 trace_vdebug ((fmt), ##args); \ |
74 } while (0) | 78 } while (0) |
75 | 79 |
76 #define trace_debug(FMT, args...) \ | 80 #define trace_debug(FMT, args...) \ |
77 trace_debug_1 (1, FMT, ##args) | 81 trace_debug_1 (1, FMT, ##args) |
78 | 82 |
79 #if defined(__GNUC__) | 83 #if defined(__GNUC__) |
80 # define ATTR_USED __attribute__((used)) | 84 # define ATTR_USED __attribute__((used)) |
81 # define ATTR_NOINLINE __attribute__((noinline)) | 85 # define ATTR_NOINLINE __attribute__((noinline)) |
82 # define ATTR_CONSTRUCTOR __attribute__ ((constructor)) | 86 # define ATTR_CONSTRUCTOR __attribute__ ((constructor)) |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
170 CORE_ADDR addr_trace_buffer_lo; | 174 CORE_ADDR addr_trace_buffer_lo; |
171 CORE_ADDR addr_trace_buffer_hi; | 175 CORE_ADDR addr_trace_buffer_hi; |
172 CORE_ADDR addr_traceframe_read_count; | 176 CORE_ADDR addr_traceframe_read_count; |
173 CORE_ADDR addr_traceframe_write_count; | 177 CORE_ADDR addr_traceframe_write_count; |
174 CORE_ADDR addr_traceframes_created; | 178 CORE_ADDR addr_traceframes_created; |
175 CORE_ADDR addr_trace_state_variables; | 179 CORE_ADDR addr_trace_state_variables; |
176 CORE_ADDR addr_get_raw_reg; | 180 CORE_ADDR addr_get_raw_reg; |
177 CORE_ADDR addr_get_trace_state_variable_value; | 181 CORE_ADDR addr_get_trace_state_variable_value; |
178 CORE_ADDR addr_set_trace_state_variable_value; | 182 CORE_ADDR addr_set_trace_state_variable_value; |
179 CORE_ADDR addr_ust_loaded; | 183 CORE_ADDR addr_ust_loaded; |
180 CORE_ADDR addr_helper_thread_id; | |
181 CORE_ADDR addr_cmd_buf; | |
182 }; | 184 }; |
183 | 185 |
184 #define STRINGIZE_1(STR) #STR | |
185 #define STRINGIZE(STR) STRINGIZE_1(STR) | |
186 #define IPA_SYM(SYM) \ | |
187 { \ | |
188 STRINGIZE (gdb_agent_ ## SYM), \ | |
189 offsetof (struct ipa_sym_addresses, addr_ ## SYM) \ | |
190 } | |
191 | |
192 static struct | 186 static struct |
193 { | 187 { |
194 const char *name; | 188 const char *name; |
195 int offset; | 189 int offset; |
196 int required; | 190 int required; |
197 } symbol_list[] = { | 191 } symbol_list[] = { |
198 IPA_SYM(gdb_tp_heap_buffer), | 192 IPA_SYM(gdb_tp_heap_buffer), |
199 IPA_SYM(gdb_jump_pad_buffer), | 193 IPA_SYM(gdb_jump_pad_buffer), |
200 IPA_SYM(gdb_jump_pad_buffer_end), | 194 IPA_SYM(gdb_jump_pad_buffer_end), |
201 IPA_SYM(gdb_trampoline_buffer), | 195 IPA_SYM(gdb_trampoline_buffer), |
(...skipping 15 matching lines...) Expand all Loading... |
217 IPA_SYM(trace_buffer_lo), | 211 IPA_SYM(trace_buffer_lo), |
218 IPA_SYM(trace_buffer_hi), | 212 IPA_SYM(trace_buffer_hi), |
219 IPA_SYM(traceframe_read_count), | 213 IPA_SYM(traceframe_read_count), |
220 IPA_SYM(traceframe_write_count), | 214 IPA_SYM(traceframe_write_count), |
221 IPA_SYM(traceframes_created), | 215 IPA_SYM(traceframes_created), |
222 IPA_SYM(trace_state_variables), | 216 IPA_SYM(trace_state_variables), |
223 IPA_SYM(get_raw_reg), | 217 IPA_SYM(get_raw_reg), |
224 IPA_SYM(get_trace_state_variable_value), | 218 IPA_SYM(get_trace_state_variable_value), |
225 IPA_SYM(set_trace_state_variable_value), | 219 IPA_SYM(set_trace_state_variable_value), |
226 IPA_SYM(ust_loaded), | 220 IPA_SYM(ust_loaded), |
227 IPA_SYM(helper_thread_id), | |
228 IPA_SYM(cmd_buf), | |
229 }; | 221 }; |
230 | 222 |
231 struct ipa_sym_addresses ipa_sym_addrs; | 223 static struct ipa_sym_addresses ipa_sym_addrs; |
232 | |
233 int all_tracepoint_symbols_looked_up; | |
234 | |
235 int | |
236 in_process_agent_loaded (void) | |
237 { | |
238 return all_tracepoint_symbols_looked_up; | |
239 } | |
240 | 224 |
241 static int read_inferior_integer (CORE_ADDR symaddr, int *val); | 225 static int read_inferior_integer (CORE_ADDR symaddr, int *val); |
242 | 226 |
243 /* Returns true if both the in-process agent library and the static | 227 /* Returns true if both the in-process agent library and the static |
244 tracepoints libraries are loaded in the inferior. */ | 228 tracepoints libraries are loaded in the inferior, and agent has |
| 229 capability on static tracepoints. */ |
245 | 230 |
246 static int | 231 static int |
247 in_process_agent_loaded_ust (void) | 232 in_process_agent_supports_ust (void) |
248 { | 233 { |
249 int loaded = 0; | 234 int loaded = 0; |
250 | 235 |
251 if (!in_process_agent_loaded ()) | 236 if (!agent_loaded_p ()) |
252 { | 237 { |
253 warning ("In-process agent not loaded"); | 238 warning ("In-process agent not loaded"); |
254 return 0; | 239 return 0; |
255 } | 240 } |
256 | 241 |
257 if (read_inferior_integer (ipa_sym_addrs.addr_ust_loaded, &loaded)) | 242 if (agent_capability_check (AGENT_CAPA_STATIC_TRACE)) |
258 { | 243 { |
259 warning ("Error reading ust_loaded in lib"); | 244 /* Agent understands static tracepoint, then check whether UST is in |
260 return 0; | 245 » fact loaded in the inferior. */ |
| 246 if (read_inferior_integer (ipa_sym_addrs.addr_ust_loaded, &loaded)) |
| 247 » { |
| 248 » warning ("Error reading ust_loaded in lib"); |
| 249 » return 0; |
| 250 » } |
| 251 |
| 252 return loaded; |
261 } | 253 } |
262 | 254 else |
263 return loaded; | 255 return 0; |
264 } | 256 } |
265 | 257 |
266 static void | 258 static void |
267 write_e_ipa_not_loaded (char *buffer) | 259 write_e_ipa_not_loaded (char *buffer) |
268 { | 260 { |
269 sprintf (buffer, | 261 sprintf (buffer, |
270 "E.In-process agent library not loaded in process. " | 262 "E.In-process agent library not loaded in process. " |
271 "Fast and static tracepoints unavailable."); | 263 "Fast and static tracepoints unavailable."); |
272 } | 264 } |
273 | 265 |
(...skipping 11 matching lines...) Expand all Loading... |
285 sprintf (buffer, "E.GDBserver was built without static tracepoints support"); | 277 sprintf (buffer, "E.GDBserver was built without static tracepoints support"); |
286 #endif | 278 #endif |
287 } | 279 } |
288 | 280 |
289 /* If the in-process agent library isn't loaded in the inferior, write | 281 /* If the in-process agent library isn't loaded in the inferior, write |
290 an error to BUFFER, and return 1. Otherwise, return 0. */ | 282 an error to BUFFER, and return 1. Otherwise, return 0. */ |
291 | 283 |
292 static int | 284 static int |
293 maybe_write_ipa_not_loaded (char *buffer) | 285 maybe_write_ipa_not_loaded (char *buffer) |
294 { | 286 { |
295 if (!in_process_agent_loaded ()) | 287 if (!agent_loaded_p ()) |
296 { | 288 { |
297 write_e_ipa_not_loaded (buffer); | 289 write_e_ipa_not_loaded (buffer); |
298 return 1; | 290 return 1; |
299 } | 291 } |
300 return 0; | 292 return 0; |
301 } | 293 } |
302 | 294 |
303 /* If the in-process agent library and the ust (static tracepoints) | 295 /* If the in-process agent library and the ust (static tracepoints) |
304 library aren't loaded in the inferior, write an error to BUFFER, | 296 library aren't loaded in the inferior, write an error to BUFFER, |
305 and return 1. Otherwise, return 0. */ | 297 and return 1. Otherwise, return 0. */ |
306 | 298 |
307 static int | 299 static int |
308 maybe_write_ipa_ust_not_loaded (char *buffer) | 300 maybe_write_ipa_ust_not_loaded (char *buffer) |
309 { | 301 { |
310 if (!in_process_agent_loaded ()) | 302 if (!agent_loaded_p ()) |
311 { | 303 { |
312 write_e_ipa_not_loaded (buffer); | 304 write_e_ipa_not_loaded (buffer); |
313 return 1; | 305 return 1; |
314 } | 306 } |
315 else if (!in_process_agent_loaded_ust ()) | 307 else if (!in_process_agent_supports_ust ()) |
316 { | 308 { |
317 write_e_ust_not_loaded (buffer); | 309 write_e_ust_not_loaded (buffer); |
318 return 1; | 310 return 1; |
319 } | 311 } |
320 return 0; | 312 return 0; |
321 } | 313 } |
322 | 314 |
323 /* Cache all future symbols that the tracepoints module might request. | 315 /* Cache all future symbols that the tracepoints module might request. |
324 We can not request symbols at arbitrary states in the remote | 316 We can not request symbols at arbitrary states in the remote |
325 protocol, only when the client tells us that new symbols are | 317 protocol, only when the client tells us that new symbols are |
326 available. So when we load the in-process library, make sure to | 318 available. So when we load the in-process library, make sure to |
327 check the entire list. */ | 319 check the entire list. */ |
328 | 320 |
329 void | 321 void |
330 tracepoint_look_up_symbols (void) | 322 tracepoint_look_up_symbols (void) |
331 { | 323 { |
332 int i; | 324 int i; |
333 | 325 |
334 if (all_tracepoint_symbols_looked_up) | 326 if (agent_loaded_p ()) |
335 return; | 327 return; |
336 | 328 |
337 for (i = 0; i < sizeof (symbol_list) / sizeof (symbol_list[0]); i++) | 329 for (i = 0; i < sizeof (symbol_list) / sizeof (symbol_list[0]); i++) |
338 { | 330 { |
339 CORE_ADDR *addrp = | 331 CORE_ADDR *addrp = |
340 (CORE_ADDR *) ((char *) &ipa_sym_addrs + symbol_list[i].offset); | 332 (CORE_ADDR *) ((char *) &ipa_sym_addrs + symbol_list[i].offset); |
341 | 333 |
342 if (look_up_one_symbol (symbol_list[i].name, addrp, 1) == 0) | 334 if (look_up_one_symbol (symbol_list[i].name, addrp, 1) == 0) |
343 { | 335 { |
344 if (debug_threads) | 336 if (debug_threads) |
345 fprintf (stderr, "symbol `%s' not found\n", symbol_list[i].name); | 337 fprintf (stderr, "symbol `%s' not found\n", symbol_list[i].name); |
346 return; | 338 return; |
347 } | 339 } |
348 } | 340 } |
349 | 341 |
350 all_tracepoint_symbols_looked_up = 1; | 342 agent_look_up_symbols (NULL); |
351 } | 343 } |
352 | 344 |
353 #endif | 345 #endif |
354 | 346 |
355 /* GDBserver places a breakpoint on the IPA's version (which is a nop) | 347 /* GDBserver places a breakpoint on the IPA's version (which is a nop) |
356 of the "stop_tracing" function. When this breakpoint is hit, | 348 of the "stop_tracing" function. When this breakpoint is hit, |
357 tracing stopped in the IPA for some reason. E.g., due to | 349 tracing stopped in the IPA for some reason. E.g., due to |
358 tracepoint reaching the pass count, hitting conditional expression | 350 tracepoint reaching the pass count, hitting conditional expression |
359 evaluation error, etc. | 351 evaluation error, etc. |
360 | 352 |
361 The IPA's trace buffer is never in circular tracing mode: instead, | 353 The IPA's trace buffer is never in circular tracing mode: instead, |
362 GDBserver's is, and whenever the in-process buffer fills, it calls | 354 GDBserver's is, and whenever the in-process buffer fills, it calls |
363 "flush_trace_buffer", which triggers an internal breakpoint. | 355 "flush_trace_buffer", which triggers an internal breakpoint. |
364 GDBserver reacts to this breakpoint by pulling the meanwhile | 356 GDBserver reacts to this breakpoint by pulling the meanwhile |
365 collected data. Old frames discarding is always handled on the | 357 collected data. Old frames discarding is always handled on the |
366 GDBserver side. */ | 358 GDBserver side. */ |
367 | 359 |
368 #ifdef IN_PROCESS_AGENT | 360 #ifdef IN_PROCESS_AGENT |
369 int debug_threads = 0; | |
370 | |
371 int | 361 int |
372 read_inferior_memory (CORE_ADDR memaddr, unsigned char *myaddr, int len) | 362 read_inferior_memory (CORE_ADDR memaddr, unsigned char *myaddr, int len) |
373 { | 363 { |
374 memcpy (myaddr, (void *) (uintptr_t) memaddr, len); | 364 memcpy (myaddr, (void *) (uintptr_t) memaddr, len); |
375 return 0; | 365 return 0; |
376 } | 366 } |
377 | 367 |
378 /* Call this in the functions where GDBserver places a breakpoint, so | 368 /* Call this in the functions where GDBserver places a breakpoint, so |
379 that the compiler doesn't try to be clever and skip calling the | 369 that the compiler doesn't try to be clever and skip calling the |
380 function at all. This is necessary, even if we tell the compiler | 370 function at all. This is necessary, even if we tell the compiler |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
412 } | 402 } |
413 | 403 |
414 /* Breakpoint at "stop_tracing" in the inferior lib. */ | 404 /* Breakpoint at "stop_tracing" in the inferior lib. */ |
415 struct breakpoint *stop_tracing_bkpt; | 405 struct breakpoint *stop_tracing_bkpt; |
416 static int stop_tracing_handler (CORE_ADDR); | 406 static int stop_tracing_handler (CORE_ADDR); |
417 | 407 |
418 /* Breakpoint at "flush_trace_buffer" in the inferior lib. */ | 408 /* Breakpoint at "flush_trace_buffer" in the inferior lib. */ |
419 struct breakpoint *flush_trace_buffer_bkpt; | 409 struct breakpoint *flush_trace_buffer_bkpt; |
420 static int flush_trace_buffer_handler (CORE_ADDR); | 410 static int flush_trace_buffer_handler (CORE_ADDR); |
421 | 411 |
422 static void download_tracepoints (void); | |
423 static void download_trace_state_variables (void); | 412 static void download_trace_state_variables (void); |
424 static void upload_fast_traceframes (void); | 413 static void upload_fast_traceframes (void); |
425 | 414 |
426 static int run_inferior_command (char *cmd); | 415 static int run_inferior_command (char *cmd, int len); |
427 | 416 |
428 static int | 417 static int |
429 read_inferior_integer (CORE_ADDR symaddr, int *val) | 418 read_inferior_integer (CORE_ADDR symaddr, int *val) |
430 { | 419 { |
431 return read_inferior_memory (symaddr, (unsigned char *) val, | 420 return read_inferior_memory (symaddr, (unsigned char *) val, |
432 sizeof (*val)); | 421 sizeof (*val)); |
433 } | 422 } |
434 | 423 |
| 424 struct tracepoint; |
| 425 static int tracepoint_send_agent (struct tracepoint *tpoint); |
| 426 |
435 static int | 427 static int |
436 read_inferior_uinteger (CORE_ADDR symaddr, unsigned int *val) | 428 read_inferior_uinteger (CORE_ADDR symaddr, unsigned int *val) |
437 { | 429 { |
438 return read_inferior_memory (symaddr, (unsigned char *) val, | 430 return read_inferior_memory (symaddr, (unsigned char *) val, |
439 sizeof (*val)); | 431 sizeof (*val)); |
440 } | 432 } |
441 | 433 |
442 static int | 434 static int |
443 read_inferior_data_pointer (CORE_ADDR symaddr, CORE_ADDR *val) | 435 read_inferior_data_pointer (CORE_ADDR symaddr, CORE_ADDR *val) |
444 { | 436 { |
(...skipping 18 matching lines...) Expand all Loading... |
463 { | 455 { |
464 return write_inferior_memory (symaddr, (unsigned char *) &val, sizeof (val)); | 456 return write_inferior_memory (symaddr, (unsigned char *) &val, sizeof (val)); |
465 } | 457 } |
466 | 458 |
467 static int | 459 static int |
468 write_inferior_uinteger (CORE_ADDR symaddr, unsigned int val) | 460 write_inferior_uinteger (CORE_ADDR symaddr, unsigned int val) |
469 { | 461 { |
470 return write_inferior_memory (symaddr, (unsigned char *) &val, sizeof (val)); | 462 return write_inferior_memory (symaddr, (unsigned char *) &val, sizeof (val)); |
471 } | 463 } |
472 | 464 |
| 465 static CORE_ADDR target_malloc (ULONGEST size); |
| 466 static int write_inferior_data_ptr (CORE_ADDR where, CORE_ADDR ptr); |
| 467 |
| 468 #define COPY_FIELD_TO_BUF(BUF, OBJ, FIELD) \ |
| 469 do { \ |
| 470 memcpy (BUF, &(OBJ)->FIELD, sizeof ((OBJ)->FIELD)); \ |
| 471 BUF += sizeof ((OBJ)->FIELD); \ |
| 472 } while (0) |
| 473 |
473 #endif | 474 #endif |
474 | 475 |
475 /* This enum must exactly match what is documented in | 476 /* Operations on various types of tracepoint actions. */ |
476 gdb/doc/agentexpr.texi, including all the numerical values. */ | |
477 | 477 |
478 enum gdb_agent_op | 478 struct tracepoint_action; |
479 { | |
480 #define DEFOP(NAME, SIZE, DATA_SIZE, CONSUMED, PRODUCED, VALUE) \ | |
481 gdb_agent_op_ ## NAME = VALUE, | |
482 #include "ax.def" | |
483 #undef DEFOP | |
484 gdb_agent_op_last | |
485 }; | |
486 | 479 |
487 static const char *gdb_agent_op_names [gdb_agent_op_last] = | 480 struct tracepoint_action_ops |
488 { | 481 { |
489 "?undef?" | 482 /* Download tracepoint action ACTION to IPA. Return the address of action |
490 #define DEFOP(NAME, SIZE, DATA_SIZE, CONSUMED, PRODUCED, VALUE) , # NAME | 483 in IPA/inferior. */ |
491 #include "ax.def" | 484 CORE_ADDR (*download) (const struct tracepoint_action *action); |
492 #undef DEFOP | |
493 }; | |
494 | 485 |
495 static const unsigned char gdb_agent_op_sizes [gdb_agent_op_last] = | 486 /* Send ACTION to agent via command buffer started from BUFFER. Return |
496 { | 487 updated head of command buffer. */ |
497 0 | 488 char* (*send) (char *buffer, const struct tracepoint_action *action); |
498 #define DEFOP(NAME, SIZE, DATA_SIZE, CONSUMED, PRODUCED, VALUE) , SIZE | |
499 #include "ax.def" | |
500 #undef DEFOP | |
501 }; | |
502 | |
503 struct agent_expr | |
504 { | |
505 int length; | |
506 | |
507 unsigned char *bytes; | |
508 }; | 489 }; |
509 | 490 |
510 /* Base action. Concrete actions inherit this. */ | 491 /* Base action. Concrete actions inherit this. */ |
511 | 492 |
512 struct tracepoint_action | 493 struct tracepoint_action |
513 { | 494 { |
| 495 #ifndef IN_PROCESS_AGENT |
| 496 const struct tracepoint_action_ops *ops; |
| 497 #endif |
514 char type; | 498 char type; |
515 }; | 499 }; |
516 | 500 |
517 /* An 'M' (collect memory) action. */ | 501 /* An 'M' (collect memory) action. */ |
518 struct collect_memory_action | 502 struct collect_memory_action |
519 { | 503 { |
520 struct tracepoint_action base; | 504 struct tracepoint_action base; |
521 | 505 |
522 ULONGEST addr; | 506 ULONGEST addr; |
523 ULONGEST len; | 507 ULONGEST len; |
524 int basereg; | 508 int32_t basereg; |
525 }; | 509 }; |
526 | 510 |
527 /* An 'R' (collect registers) action. */ | 511 /* An 'R' (collect registers) action. */ |
528 | 512 |
529 struct collect_registers_action | 513 struct collect_registers_action |
530 { | 514 { |
531 struct tracepoint_action base; | 515 struct tracepoint_action base; |
532 }; | 516 }; |
533 | 517 |
534 /* An 'X' (evaluate expression) action. */ | 518 /* An 'X' (evaluate expression) action. */ |
535 | 519 |
536 struct eval_expr_action | 520 struct eval_expr_action |
537 { | 521 { |
538 struct tracepoint_action base; | 522 struct tracepoint_action base; |
539 | 523 |
540 struct agent_expr *expr; | 524 struct agent_expr *expr; |
541 }; | 525 }; |
542 | 526 |
543 /* An 'L' (collect static trace data) action. */ | 527 /* An 'L' (collect static trace data) action. */ |
544 struct collect_static_trace_data_action | 528 struct collect_static_trace_data_action |
545 { | 529 { |
546 struct tracepoint_action base; | 530 struct tracepoint_action base; |
547 }; | 531 }; |
548 | 532 |
| 533 #ifndef IN_PROCESS_AGENT |
| 534 static CORE_ADDR |
| 535 m_tracepoint_action_download (const struct tracepoint_action *action) |
| 536 { |
| 537 int size_in_ipa = (sizeof (struct collect_memory_action) |
| 538 - offsetof (struct tracepoint_action, type)); |
| 539 CORE_ADDR ipa_action = target_malloc (size_in_ipa); |
| 540 |
| 541 write_inferior_memory (ipa_action, (unsigned char *) &action->type, |
| 542 size_in_ipa); |
| 543 |
| 544 return ipa_action; |
| 545 } |
| 546 static char * |
| 547 m_tracepoint_action_send (char *buffer, const struct tracepoint_action *action) |
| 548 { |
| 549 struct collect_memory_action *maction |
| 550 = (struct collect_memory_action *) action; |
| 551 |
| 552 COPY_FIELD_TO_BUF (buffer, maction, addr); |
| 553 COPY_FIELD_TO_BUF (buffer, maction, len); |
| 554 COPY_FIELD_TO_BUF (buffer, maction, basereg); |
| 555 |
| 556 return buffer; |
| 557 } |
| 558 |
| 559 static const struct tracepoint_action_ops m_tracepoint_action_ops = |
| 560 { |
| 561 m_tracepoint_action_download, |
| 562 m_tracepoint_action_send, |
| 563 }; |
| 564 |
| 565 static CORE_ADDR |
| 566 r_tracepoint_action_download (const struct tracepoint_action *action) |
| 567 { |
| 568 int size_in_ipa = (sizeof (struct collect_registers_action) |
| 569 - offsetof (struct tracepoint_action, type)); |
| 570 CORE_ADDR ipa_action = target_malloc (size_in_ipa); |
| 571 |
| 572 write_inferior_memory (ipa_action, (unsigned char *) &action->type, |
| 573 size_in_ipa); |
| 574 |
| 575 return ipa_action; |
| 576 } |
| 577 |
| 578 static char * |
| 579 r_tracepoint_action_send (char *buffer, const struct tracepoint_action *action) |
| 580 { |
| 581 return buffer; |
| 582 } |
| 583 |
| 584 static const struct tracepoint_action_ops r_tracepoint_action_ops = |
| 585 { |
| 586 r_tracepoint_action_download, |
| 587 r_tracepoint_action_send, |
| 588 }; |
| 589 |
| 590 static CORE_ADDR download_agent_expr (struct agent_expr *expr); |
| 591 |
| 592 static CORE_ADDR |
| 593 x_tracepoint_action_download (const struct tracepoint_action *action) |
| 594 { |
| 595 int size_in_ipa = (sizeof (struct eval_expr_action) |
| 596 - offsetof (struct tracepoint_action, type)); |
| 597 CORE_ADDR ipa_action = target_malloc (size_in_ipa); |
| 598 CORE_ADDR expr; |
| 599 |
| 600 write_inferior_memory (ipa_action, (unsigned char *) &action->type, |
| 601 size_in_ipa); |
| 602 expr = download_agent_expr (((struct eval_expr_action *)action)->expr); |
| 603 write_inferior_data_ptr (ipa_action + offsetof (struct eval_expr_action, expr) |
| 604 - offsetof (struct tracepoint_action, type), |
| 605 expr); |
| 606 |
| 607 return ipa_action; |
| 608 } |
| 609 |
| 610 /* Copy agent expression AEXPR to buffer pointed by P. If AEXPR is NULL, |
| 611 copy 0 to P. Return updated header of buffer. */ |
| 612 |
| 613 static char * |
| 614 agent_expr_send (char *p, const struct agent_expr *aexpr) |
| 615 { |
| 616 /* Copy the length of condition first, and then copy its |
| 617 content. */ |
| 618 if (aexpr == NULL) |
| 619 { |
| 620 memset (p, 0, 4); |
| 621 p += 4; |
| 622 } |
| 623 else |
| 624 { |
| 625 memcpy (p, &aexpr->length, 4); |
| 626 p +=4; |
| 627 |
| 628 memcpy (p, aexpr->bytes, aexpr->length); |
| 629 p += aexpr->length; |
| 630 } |
| 631 return p; |
| 632 } |
| 633 |
| 634 static char * |
| 635 x_tracepoint_action_send ( char *buffer, const struct tracepoint_action *action) |
| 636 { |
| 637 struct eval_expr_action *eaction = (struct eval_expr_action *) action; |
| 638 |
| 639 return agent_expr_send (buffer, eaction->expr); |
| 640 } |
| 641 |
| 642 static const struct tracepoint_action_ops x_tracepoint_action_ops = |
| 643 { |
| 644 x_tracepoint_action_download, |
| 645 x_tracepoint_action_send, |
| 646 }; |
| 647 |
| 648 static CORE_ADDR |
| 649 l_tracepoint_action_download (const struct tracepoint_action *action) |
| 650 { |
| 651 int size_in_ipa = (sizeof (struct collect_static_trace_data_action) |
| 652 - offsetof (struct tracepoint_action, type)); |
| 653 CORE_ADDR ipa_action = target_malloc (size_in_ipa); |
| 654 |
| 655 write_inferior_memory (ipa_action, (unsigned char *) &action->type, |
| 656 size_in_ipa); |
| 657 |
| 658 return ipa_action; |
| 659 } |
| 660 |
| 661 static char * |
| 662 l_tracepoint_action_send (char *buffer, const struct tracepoint_action *action) |
| 663 { |
| 664 return buffer; |
| 665 } |
| 666 |
| 667 static const struct tracepoint_action_ops l_tracepoint_action_ops = |
| 668 { |
| 669 l_tracepoint_action_download, |
| 670 l_tracepoint_action_send, |
| 671 }; |
| 672 #endif |
| 673 |
549 /* This structure describes a piece of the source-level definition of | 674 /* This structure describes a piece of the source-level definition of |
550 the tracepoint. The contents are not interpreted by the target, | 675 the tracepoint. The contents are not interpreted by the target, |
551 but preserved verbatim for uploading upon reconnection. */ | 676 but preserved verbatim for uploading upon reconnection. */ |
552 | 677 |
553 struct source_string | 678 struct source_string |
554 { | 679 { |
555 /* The type of string, such as "cond" for a conditional. */ | 680 /* The type of string, such as "cond" for a conditional. */ |
556 char *type; | 681 char *type; |
557 | 682 |
558 /* The source-level string itself. For the sake of target | 683 /* The source-level string itself. For the sake of target |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
593 location. Our target version of tracepoints is more like GDB's | 718 location. Our target version of tracepoints is more like GDB's |
594 notion of "breakpoint locations", but we have almost nothing that | 719 notion of "breakpoint locations", but we have almost nothing that |
595 is not per-location, so we bother having two kinds of objects. The | 720 is not per-location, so we bother having two kinds of objects. The |
596 key consequence is that numbers are not unique, and that it takes | 721 key consequence is that numbers are not unique, and that it takes |
597 both number and address to identify a tracepoint uniquely. */ | 722 both number and address to identify a tracepoint uniquely. */ |
598 | 723 |
599 struct tracepoint | 724 struct tracepoint |
600 { | 725 { |
601 /* The number of the tracepoint, as specified by GDB. Several | 726 /* The number of the tracepoint, as specified by GDB. Several |
602 tracepoint objects here may share a number. */ | 727 tracepoint objects here may share a number. */ |
603 int number; | 728 uint32_t number; |
604 | 729 |
605 /* Address at which the tracepoint is supposed to trigger. Several | 730 /* Address at which the tracepoint is supposed to trigger. Several |
606 tracepoints may share an address. */ | 731 tracepoints may share an address. */ |
607 CORE_ADDR address; | 732 CORE_ADDR address; |
608 | 733 |
609 /* Tracepoint type. */ | 734 /* Tracepoint type. */ |
610 enum tracepoint_type type; | 735 enum tracepoint_type type; |
611 | 736 |
612 /* True if the tracepoint is currently enabled. */ | 737 /* True if the tracepoint is currently enabled. */ |
613 int enabled; | 738 int8_t enabled; |
614 | 739 |
615 /* The number of single steps that will be performed after each | 740 /* The number of single steps that will be performed after each |
616 tracepoint hit. */ | 741 tracepoint hit. */ |
617 long step_count; | 742 uint64_t step_count; |
618 | 743 |
619 /* The number of times the tracepoint may be hit before it will | 744 /* The number of times the tracepoint may be hit before it will |
620 terminate the entire tracing run. */ | 745 terminate the entire tracing run. */ |
621 long pass_count; | 746 uint64_t pass_count; |
622 | 747 |
623 /* Pointer to the agent expression that is the tracepoint's | 748 /* Pointer to the agent expression that is the tracepoint's |
624 conditional, or NULL if the tracepoint is unconditional. */ | 749 conditional, or NULL if the tracepoint is unconditional. */ |
625 struct agent_expr *cond; | 750 struct agent_expr *cond; |
626 | 751 |
627 /* The list of actions to take when the tracepoint triggers. */ | 752 /* The list of actions to take when the tracepoint triggers. */ |
628 int numactions; | 753 uint32_t numactions; |
629 struct tracepoint_action **actions; | 754 struct tracepoint_action **actions; |
630 | 755 |
631 /* Count of the times we've hit this tracepoint during the run. | 756 /* Count of the times we've hit this tracepoint during the run. |
632 Note that while-stepping steps are not counted as "hits". */ | 757 Note that while-stepping steps are not counted as "hits". */ |
633 long hit_count; | 758 uint64_t hit_count; |
634 | 759 |
635 /* Cached sum of the sizes of traceframes created by this point. */ | 760 /* Cached sum of the sizes of traceframes created by this point. */ |
636 long traceframe_usage; | 761 uint64_t traceframe_usage; |
637 | 762 |
638 CORE_ADDR compiled_cond; | 763 CORE_ADDR compiled_cond; |
639 | 764 |
640 /* Link to the next tracepoint in the list. */ | 765 /* Link to the next tracepoint in the list. */ |
641 struct tracepoint *next; | 766 struct tracepoint *next; |
642 | 767 |
643 #ifndef IN_PROCESS_AGENT | 768 #ifndef IN_PROCESS_AGENT |
644 /* The list of actions to take when the tracepoint triggers, in | 769 /* The list of actions to take when the tracepoint triggers, in |
645 string/packet form. */ | 770 string/packet form. */ |
646 char **actions_str; | 771 char **actions_str; |
647 | 772 |
648 /* The collection of strings that describe the tracepoint as it was | 773 /* The collection of strings that describe the tracepoint as it was |
649 entered into GDB. These are not used by the target, but are | 774 entered into GDB. These are not used by the target, but are |
650 reported back to GDB upon reconnection. */ | 775 reported back to GDB upon reconnection. */ |
651 struct source_string *source_strings; | 776 struct source_string *source_strings; |
652 | 777 |
653 /* The number of bytes displaced by fast tracepoints. It may subsume | 778 /* The number of bytes displaced by fast tracepoints. It may subsume |
654 multiple instructions, for multi-byte fast tracepoints. This | 779 multiple instructions, for multi-byte fast tracepoints. This |
655 field is only valid for fast tracepoints. */ | 780 field is only valid for fast tracepoints. */ |
656 int orig_size; | 781 uint32_t orig_size; |
657 | 782 |
658 /* Only for fast tracepoints. */ | 783 /* Only for fast tracepoints. */ |
659 CORE_ADDR obj_addr_on_target; | 784 CORE_ADDR obj_addr_on_target; |
660 | 785 |
661 /* Address range where the original instruction under a fast | 786 /* Address range where the original instruction under a fast |
662 tracepoint was relocated to. (_end is actually one byte past | 787 tracepoint was relocated to. (_end is actually one byte past |
663 the end). */ | 788 the end). */ |
664 CORE_ADDR adjusted_insn_addr; | 789 CORE_ADDR adjusted_insn_addr; |
665 CORE_ADDR adjusted_insn_addr_end; | 790 CORE_ADDR adjusted_insn_addr_end; |
666 | 791 |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
731 #endif | 856 #endif |
732 | 857 |
733 /* The first tracepoint to exceed its pass count. */ | 858 /* The first tracepoint to exceed its pass count. */ |
734 | 859 |
735 IP_AGENT_EXPORT struct tracepoint *stopping_tracepoint; | 860 IP_AGENT_EXPORT struct tracepoint *stopping_tracepoint; |
736 | 861 |
737 /* True if the trace buffer is full or otherwise no longer usable. */ | 862 /* True if the trace buffer is full or otherwise no longer usable. */ |
738 | 863 |
739 IP_AGENT_EXPORT int trace_buffer_is_full; | 864 IP_AGENT_EXPORT int trace_buffer_is_full; |
740 | 865 |
741 /* Enumeration of the different kinds of things that can happen during | |
742 agent expression evaluation. */ | |
743 | |
744 enum eval_result_type | |
745 { | |
746 expr_eval_no_error, | |
747 expr_eval_empty_expression, | |
748 expr_eval_empty_stack, | |
749 expr_eval_stack_overflow, | |
750 expr_eval_stack_underflow, | |
751 expr_eval_unhandled_opcode, | |
752 expr_eval_unrecognized_opcode, | |
753 expr_eval_divide_by_zero, | |
754 expr_eval_invalid_goto | |
755 }; | |
756 | |
757 static enum eval_result_type expr_eval_result = expr_eval_no_error; | 866 static enum eval_result_type expr_eval_result = expr_eval_no_error; |
758 | 867 |
759 #ifndef IN_PROCESS_AGENT | 868 #ifndef IN_PROCESS_AGENT |
760 | 869 |
761 static const char *eval_result_names[] = | 870 static const char *eval_result_names[] = |
762 { | 871 { |
763 "terror:in the attic", /* this should never be reported */ | 872 "terror:in the attic", /* this should never be reported */ |
764 "terror:empty expression", | 873 "terror:empty expression", |
765 "terror:empty stack", | 874 "terror:empty stack", |
766 "terror:stack overflow", | 875 "terror:stack overflow", |
(...skipping 463 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1230 collect_data_at_tracepoint. */ | 1339 collect_data_at_tracepoint. */ |
1231 struct trap_tracepoint_ctx | 1340 struct trap_tracepoint_ctx |
1232 { | 1341 { |
1233 struct tracepoint_hit_ctx base; | 1342 struct tracepoint_hit_ctx base; |
1234 | 1343 |
1235 struct regcache *regcache; | 1344 struct regcache *regcache; |
1236 }; | 1345 }; |
1237 | 1346 |
1238 #endif | 1347 #endif |
1239 | 1348 |
1240 #ifndef IN_PROCESS_AGENT | 1349 static enum eval_result_type |
1241 static struct agent_expr *parse_agent_expr (char **actparm); | 1350 eval_tracepoint_agent_expr (struct tracepoint_hit_ctx *ctx, |
1242 static char *unparse_agent_expr (struct agent_expr *aexpr); | 1351 » » » struct traceframe *tframe, |
1243 #endif | 1352 » » » struct agent_expr *aexpr, |
1244 static enum eval_result_type eval_agent_expr (struct tracepoint_hit_ctx *ctx, | 1353 » » » ULONGEST *rslt); |
1245 » » » » » struct traceframe *tframe, | |
1246 » » » » » struct agent_expr *aexpr, | |
1247 » » » » » ULONGEST *rslt); | |
1248 | |
1249 static int agent_mem_read (struct traceframe *tframe, | |
1250 » » » unsigned char *to, CORE_ADDR from, ULONGEST len); | |
1251 static int agent_mem_read_string (struct traceframe *tframe, | |
1252 » » » » unsigned char *to, CORE_ADDR from, | |
1253 » » » » ULONGEST len); | |
1254 static int agent_tsv_read (struct traceframe *tframe, int n); | |
1255 | 1354 |
1256 #ifndef IN_PROCESS_AGENT | 1355 #ifndef IN_PROCESS_AGENT |
1257 static CORE_ADDR traceframe_get_pc (struct traceframe *tframe); | 1356 static CORE_ADDR traceframe_get_pc (struct traceframe *tframe); |
1258 static int traceframe_read_tsv (int num, LONGEST *val); | 1357 static int traceframe_read_tsv (int num, LONGEST *val); |
1259 #endif | 1358 #endif |
1260 | 1359 |
1261 static int condition_true_at_tracepoint (struct tracepoint_hit_ctx *ctx, | 1360 static int condition_true_at_tracepoint (struct tracepoint_hit_ctx *ctx, |
1262 struct tracepoint *tpoint); | 1361 struct tracepoint *tpoint); |
1263 | 1362 |
1264 #ifndef IN_PROCESS_AGENT | 1363 #ifndef IN_PROCESS_AGENT |
(...skipping 16 matching lines...) Expand all Loading... |
1281 struct tracepoint *tpoint, | 1380 struct tracepoint *tpoint, |
1282 struct traceframe *tframe, | 1381 struct traceframe *tframe, |
1283 struct tracepoint_action *taction); | 1382 struct tracepoint_action *taction); |
1284 | 1383 |
1285 #ifndef IN_PROCESS_AGENT | 1384 #ifndef IN_PROCESS_AGENT |
1286 static struct tracepoint *fast_tracepoint_from_ipa_tpoint_address (CORE_ADDR); | 1385 static struct tracepoint *fast_tracepoint_from_ipa_tpoint_address (CORE_ADDR); |
1287 | 1386 |
1288 static void install_tracepoint (struct tracepoint *, char *own_buf); | 1387 static void install_tracepoint (struct tracepoint *, char *own_buf); |
1289 static void download_tracepoint (struct tracepoint *); | 1388 static void download_tracepoint (struct tracepoint *); |
1290 static int install_fast_tracepoint (struct tracepoint *, char *errbuf); | 1389 static int install_fast_tracepoint (struct tracepoint *, char *errbuf); |
| 1390 static void clone_fast_tracepoint (struct tracepoint *to, |
| 1391 const struct tracepoint *from); |
1291 #endif | 1392 #endif |
1292 | 1393 |
1293 static LONGEST get_timestamp (void); | 1394 static LONGEST get_timestamp (void); |
1294 | 1395 |
1295 #if defined(__GNUC__) | 1396 #if defined(__GNUC__) |
1296 # define memory_barrier() asm volatile ("" : : : "memory") | 1397 # define memory_barrier() asm volatile ("" : : : "memory") |
1297 #else | 1398 #else |
1298 # define memory_barrier() do {} while (0) | 1399 # define memory_barrier() do {} while (0) |
1299 #endif | 1400 #endif |
1300 | 1401 |
1301 /* We only build the IPA if this builtin is supported, and there are | 1402 /* We only build the IPA if this builtin is supported, and there are |
1302 no uses of this in GDBserver itself, so we're safe in defining this | 1403 no uses of this in GDBserver itself, so we're safe in defining this |
1303 unconditionally. */ | 1404 unconditionally. */ |
1304 #define cmpxchg(mem, oldval, newval) \ | 1405 #define cmpxchg(mem, oldval, newval) \ |
1305 __sync_val_compare_and_swap (mem, oldval, newval) | 1406 __sync_val_compare_and_swap (mem, oldval, newval) |
1306 | 1407 |
1307 /* The size in bytes of the buffer used to talk to the IPA helper | |
1308 thread. */ | |
1309 #define CMD_BUF_SIZE 1024 | |
1310 | |
1311 /* Record that an error occurred during expression evaluation. */ | 1408 /* Record that an error occurred during expression evaluation. */ |
1312 | 1409 |
1313 static void | 1410 static void |
1314 record_tracepoint_error (struct tracepoint *tpoint, const char *which, | 1411 record_tracepoint_error (struct tracepoint *tpoint, const char *which, |
1315 enum eval_result_type rtype) | 1412 enum eval_result_type rtype) |
1316 { | 1413 { |
1317 trace_debug ("Tracepoint %d at %s %s eval reports error %d", | 1414 trace_debug ("Tracepoint %d at %s %s eval reports error %d", |
1318 tpoint->number, paddress (tpoint->address), which, rtype); | 1415 tpoint->number, paddress (tpoint->address), which, rtype); |
1319 | 1416 |
1320 #ifdef IN_PROCESS_AGENT | 1417 #ifdef IN_PROCESS_AGENT |
(...skipping 432 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1753 { | 1850 { |
1754 struct tracepoint *tpoint; | 1851 struct tracepoint *tpoint; |
1755 | 1852 |
1756 for (tpoint = tracepoints; tpoint; tpoint = tpoint->next) | 1853 for (tpoint = tracepoints; tpoint; tpoint = tpoint->next) |
1757 if (tpoint->number == id && tpoint->address == addr) | 1854 if (tpoint->number == id && tpoint->address == addr) |
1758 return tpoint; | 1855 return tpoint; |
1759 | 1856 |
1760 return NULL; | 1857 return NULL; |
1761 } | 1858 } |
1762 | 1859 |
| 1860 /* Remove TPOINT from global list. */ |
| 1861 |
| 1862 static void |
| 1863 remove_tracepoint (struct tracepoint *tpoint) |
| 1864 { |
| 1865 struct tracepoint *tp, *tp_prev; |
| 1866 |
| 1867 for (tp = tracepoints, tp_prev = NULL; tp && tp != tpoint; |
| 1868 tp_prev = tp, tp = tp->next) |
| 1869 ; |
| 1870 |
| 1871 if (tp) |
| 1872 { |
| 1873 if (tp_prev) |
| 1874 tp_prev->next = tp->next; |
| 1875 else |
| 1876 tracepoints = tp->next; |
| 1877 |
| 1878 xfree (tp); |
| 1879 } |
| 1880 } |
| 1881 |
1763 /* There may be several tracepoints with the same number (because they | 1882 /* There may be several tracepoints with the same number (because they |
1764 are "locations", in GDB parlance); return the next one after the | 1883 are "locations", in GDB parlance); return the next one after the |
1765 given tracepoint, or search from the beginning of the list if the | 1884 given tracepoint, or search from the beginning of the list if the |
1766 first argument is NULL. */ | 1885 first argument is NULL. */ |
1767 | 1886 |
1768 static struct tracepoint * | 1887 static struct tracepoint * |
1769 find_next_tracepoint_by_number (struct tracepoint *prev_tp, int num) | 1888 find_next_tracepoint_by_number (struct tracepoint *prev_tp, int num) |
1770 { | 1889 { |
1771 struct tracepoint *tpoint; | 1890 struct tracepoint *tpoint; |
1772 | 1891 |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1818 switch (*act) | 1937 switch (*act) |
1819 { | 1938 { |
1820 case 'M': | 1939 case 'M': |
1821 { | 1940 { |
1822 struct collect_memory_action *maction; | 1941 struct collect_memory_action *maction; |
1823 ULONGEST basereg; | 1942 ULONGEST basereg; |
1824 int is_neg; | 1943 int is_neg; |
1825 | 1944 |
1826 maction = xmalloc (sizeof *maction); | 1945 maction = xmalloc (sizeof *maction); |
1827 maction->base.type = *act; | 1946 maction->base.type = *act; |
| 1947 maction->base.ops = &m_tracepoint_action_ops; |
1828 action = &maction->base; | 1948 action = &maction->base; |
1829 | 1949 |
1830 ++act; | 1950 ++act; |
1831 is_neg = (*act == '-'); | 1951 is_neg = (*act == '-'); |
1832 if (*act == '-') | 1952 if (*act == '-') |
1833 ++act; | 1953 ++act; |
1834 act = unpack_varlen_hex (act, &basereg); | 1954 act = unpack_varlen_hex (act, &basereg); |
1835 ++act; | 1955 ++act; |
1836 act = unpack_varlen_hex (act, &maction->addr); | 1956 act = unpack_varlen_hex (act, &maction->addr); |
1837 ++act; | 1957 ++act; |
1838 act = unpack_varlen_hex (act, &maction->len); | 1958 act = unpack_varlen_hex (act, &maction->len); |
1839 maction->basereg = (is_neg | 1959 maction->basereg = (is_neg |
1840 ? - (int) basereg | 1960 ? - (int) basereg |
1841 : (int) basereg); | 1961 : (int) basereg); |
1842 trace_debug ("Want to collect %s bytes at 0x%s (basereg %d)", | 1962 trace_debug ("Want to collect %s bytes at 0x%s (basereg %d)", |
1843 pulongest (maction->len), | 1963 pulongest (maction->len), |
1844 paddress (maction->addr), maction->basereg); | 1964 paddress (maction->addr), maction->basereg); |
1845 break; | 1965 break; |
1846 } | 1966 } |
1847 case 'R': | 1967 case 'R': |
1848 { | 1968 { |
1849 struct collect_registers_action *raction; | 1969 struct collect_registers_action *raction; |
1850 | 1970 |
1851 raction = xmalloc (sizeof *raction); | 1971 raction = xmalloc (sizeof *raction); |
1852 raction->base.type = *act; | 1972 raction->base.type = *act; |
| 1973 raction->base.ops = &r_tracepoint_action_ops; |
1853 action = &raction->base; | 1974 action = &raction->base; |
1854 | 1975 |
1855 trace_debug ("Want to collect registers"); | 1976 trace_debug ("Want to collect registers"); |
1856 ++act; | 1977 ++act; |
1857 /* skip past hex digits of mask for now */ | 1978 /* skip past hex digits of mask for now */ |
1858 while (isxdigit(*act)) | 1979 while (isxdigit(*act)) |
1859 ++act; | 1980 ++act; |
1860 break; | 1981 break; |
1861 } | 1982 } |
1862 case 'L': | 1983 case 'L': |
1863 { | 1984 { |
1864 struct collect_static_trace_data_action *raction; | 1985 struct collect_static_trace_data_action *raction; |
1865 | 1986 |
1866 raction = xmalloc (sizeof *raction); | 1987 raction = xmalloc (sizeof *raction); |
1867 raction->base.type = *act; | 1988 raction->base.type = *act; |
| 1989 raction->base.ops = &l_tracepoint_action_ops; |
1868 action = &raction->base; | 1990 action = &raction->base; |
1869 | 1991 |
1870 trace_debug ("Want to collect static trace data"); | 1992 trace_debug ("Want to collect static trace data"); |
1871 ++act; | 1993 ++act; |
1872 break; | 1994 break; |
1873 } | 1995 } |
1874 case 'S': | 1996 case 'S': |
1875 trace_debug ("Unexpected step action, ignoring"); | 1997 trace_debug ("Unexpected step action, ignoring"); |
1876 ++act; | 1998 ++act; |
1877 break; | 1999 break; |
1878 case 'X': | 2000 case 'X': |
1879 { | 2001 { |
1880 struct eval_expr_action *xaction; | 2002 struct eval_expr_action *xaction; |
1881 | 2003 |
1882 xaction = xmalloc (sizeof (*xaction)); | 2004 xaction = xmalloc (sizeof (*xaction)); |
1883 xaction->base.type = *act; | 2005 xaction->base.type = *act; |
| 2006 xaction->base.ops = &x_tracepoint_action_ops; |
1884 action = &xaction->base; | 2007 action = &xaction->base; |
1885 | 2008 |
1886 trace_debug ("Want to evaluate expression"); | 2009 trace_debug ("Want to evaluate expression"); |
1887 » xaction->expr = parse_agent_expr (&act); | 2010 » xaction->expr = gdb_parse_agent_expr (&act); |
1888 break; | 2011 break; |
1889 } | 2012 } |
1890 default: | 2013 default: |
1891 trace_debug ("unknown trace action '%c', ignoring...", *act); | 2014 trace_debug ("unknown trace action '%c', ignoring...", *act); |
1892 break; | 2015 break; |
1893 case '-': | 2016 case '-': |
1894 break; | 2017 break; |
1895 } | 2018 } |
1896 | 2019 |
1897 if (action == NULL) | 2020 if (action == NULL) |
(...skipping 123 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2021 | 2144 |
2022 if (!tsv) | 2145 if (!tsv) |
2023 { | 2146 { |
2024 trace_debug ("No trace state variable %d, skipping value set", num); | 2147 trace_debug ("No trace state variable %d, skipping value set", num); |
2025 return; | 2148 return; |
2026 } | 2149 } |
2027 | 2150 |
2028 tsv->value = val; | 2151 tsv->value = val; |
2029 } | 2152 } |
2030 | 2153 |
| 2154 LONGEST |
| 2155 agent_get_trace_state_variable_value (int num) |
| 2156 { |
| 2157 return get_trace_state_variable_value (num); |
| 2158 } |
| 2159 |
| 2160 void |
| 2161 agent_set_trace_state_variable_value (int num, LONGEST val) |
| 2162 { |
| 2163 set_trace_state_variable_value (num, val); |
| 2164 } |
| 2165 |
2031 static void | 2166 static void |
2032 set_trace_state_variable_name (int num, const char *name) | 2167 set_trace_state_variable_name (int num, const char *name) |
2033 { | 2168 { |
2034 struct trace_state_variable *tsv; | 2169 struct trace_state_variable *tsv; |
2035 | 2170 |
2036 tsv = get_trace_state_variable (num); | 2171 tsv = get_trace_state_variable (num); |
2037 | 2172 |
2038 if (!tsv) | 2173 if (!tsv) |
2039 { | 2174 { |
2040 trace_debug ("No trace state variable %d, skipping name set", num); | 2175 trace_debug ("No trace state variable %d, skipping name set", num); |
(...skipping 219 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2260 clear_inferior_trace_buffer (); | 2395 clear_inferior_trace_buffer (); |
2261 | 2396 |
2262 write_ok (packet); | 2397 write_ok (packet); |
2263 } | 2398 } |
2264 | 2399 |
2265 /* Unprobe the UST marker at ADDRESS. */ | 2400 /* Unprobe the UST marker at ADDRESS. */ |
2266 | 2401 |
2267 static void | 2402 static void |
2268 unprobe_marker_at (CORE_ADDR address) | 2403 unprobe_marker_at (CORE_ADDR address) |
2269 { | 2404 { |
2270 char cmd[CMD_BUF_SIZE]; | 2405 char cmd[IPA_CMD_BUF_SIZE]; |
2271 | 2406 |
2272 sprintf (cmd, "unprobe_marker_at:%s", paddress (address)); | 2407 sprintf (cmd, "unprobe_marker_at:%s", paddress (address)); |
2273 run_inferior_command (cmd); | 2408 run_inferior_command (cmd, strlen (cmd) + 1); |
2274 } | 2409 } |
2275 | 2410 |
2276 /* Restore the program to its pre-tracing state. This routine may be called | 2411 /* Restore the program to its pre-tracing state. This routine may be called |
2277 in error situations, so it needs to be careful about only restoring | 2412 in error situations, so it needs to be careful about only restoring |
2278 from known-valid bits. */ | 2413 from known-valid bits. */ |
2279 | 2414 |
2280 static void | 2415 static void |
2281 clear_installed_tracepoints (void) | 2416 clear_installed_tracepoints (void) |
2282 { | 2417 { |
2283 struct tracepoint *tpoint; | 2418 struct tracepoint *tpoint; |
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2397 tpoint->orig_size = count; | 2532 tpoint->orig_size = count; |
2398 } | 2533 } |
2399 else if (*packet == 'S') | 2534 else if (*packet == 'S') |
2400 { | 2535 { |
2401 tpoint->type = static_tracepoint; | 2536 tpoint->type = static_tracepoint; |
2402 ++packet; | 2537 ++packet; |
2403 } | 2538 } |
2404 else if (*packet == 'X') | 2539 else if (*packet == 'X') |
2405 { | 2540 { |
2406 actparm = (char *) packet; | 2541 actparm = (char *) packet; |
2407 » tpoint->cond = parse_agent_expr (&actparm); | 2542 » tpoint->cond = gdb_parse_agent_expr (&actparm); |
2408 packet = actparm; | 2543 packet = actparm; |
2409 } | 2544 } |
2410 else if (*packet == '-') | 2545 else if (*packet == '-') |
2411 break; | 2546 break; |
2412 else if (*packet == '\0') | 2547 else if (*packet == '\0') |
2413 break; | 2548 break; |
2414 else | 2549 else |
2415 trace_debug ("Unknown optional tracepoint field"); | 2550 trace_debug ("Unknown optional tracepoint field"); |
2416 } | 2551 } |
2417 if (*packet == '-') | 2552 if (*packet == '-') |
2418 { | 2553 { |
2419 trail_hyphen = 1; | 2554 trail_hyphen = 1; |
2420 trace_debug ("Also has actions\n"); | 2555 trace_debug ("Also has actions\n"); |
2421 } | 2556 } |
2422 | 2557 |
2423 trace_debug ("Defined %stracepoint %d at 0x%s, " | 2558 trace_debug ("Defined %stracepoint %d at 0x%s, " |
2424 » » "enabled %d step %ld pass %ld", | 2559 » » "enabled %d step %" PRIu64 " pass %" PRIu64, |
2425 tpoint->type == fast_tracepoint ? "fast " | 2560 tpoint->type == fast_tracepoint ? "fast " |
2426 » » : "", | 2561 » » : tpoint->type == static_tracepoint ? "static " : "", |
2427 tpoint->number, paddress (tpoint->address), tpoint->enabled, | 2562 tpoint->number, paddress (tpoint->address), tpoint->enabled, |
2428 tpoint->step_count, tpoint->pass_count); | 2563 tpoint->step_count, tpoint->pass_count); |
2429 } | 2564 } |
2430 else if (tpoint) | 2565 else if (tpoint) |
2431 add_tracepoint_action (tpoint, packet); | 2566 add_tracepoint_action (tpoint, packet); |
2432 else | 2567 else |
2433 { | 2568 { |
2434 trace_debug ("Tracepoint error: tracepoint %d at 0x%s not found", | 2569 trace_debug ("Tracepoint error: tracepoint %d at 0x%s not found", |
2435 (int) num, paddress (addr)); | 2570 (int) num, paddress (addr)); |
2436 write_enn (own_buf); | 2571 write_enn (own_buf); |
2437 return; | 2572 return; |
2438 } | 2573 } |
2439 | 2574 |
2440 /* Install tracepoint during tracing only once for each tracepoint location. | 2575 /* Install tracepoint during tracing only once for each tracepoint location. |
2441 For each tracepoint loc, GDB may send multiple QTDP packets, and we can | 2576 For each tracepoint loc, GDB may send multiple QTDP packets, and we can |
2442 determine the last QTDP packet for one tracepoint location by checking | 2577 determine the last QTDP packet for one tracepoint location by checking |
2443 trailing hyphen in QTDP packet. */ | 2578 trailing hyphen in QTDP packet. */ |
2444 if (tracing && !trail_hyphen) | 2579 if (tracing && !trail_hyphen) |
2445 { | 2580 { |
| 2581 struct tracepoint *tp = NULL; |
| 2582 |
2446 /* Pause all threads temporarily while we patch tracepoints. */ | 2583 /* Pause all threads temporarily while we patch tracepoints. */ |
2447 pause_all (0); | 2584 pause_all (0); |
2448 | 2585 |
2449 /* download_tracepoint will update global `tracepoints' | 2586 /* download_tracepoint will update global `tracepoints' |
2450 list, so it is unsafe to leave threads in jump pad. */ | 2587 list, so it is unsafe to leave threads in jump pad. */ |
2451 stabilize_threads (); | 2588 stabilize_threads (); |
2452 | 2589 |
2453 /* Freeze threads. */ | 2590 /* Freeze threads. */ |
2454 pause_all (1); | 2591 pause_all (1); |
2455 | 2592 |
2456 download_tracepoint (tpoint); | 2593 |
2457 install_tracepoint (tpoint, own_buf); | 2594 if (tpoint->type != trap_tracepoint) |
| 2595 » { |
| 2596 » /* Find another fast or static tracepoint at the same address. */ |
| 2597 » for (tp = tracepoints; tp; tp = tp->next) |
| 2598 » { |
| 2599 » if (tp->address == tpoint->address && tp->type == tpoint->type |
| 2600 » » && tp->number != tpoint->number) |
| 2601 » » break; |
| 2602 » } |
| 2603 |
| 2604 » /* TPOINT is installed at the same address as TP. */ |
| 2605 » if (tp) |
| 2606 » { |
| 2607 » if (tpoint->type == fast_tracepoint) |
| 2608 » » clone_fast_tracepoint (tpoint, tp); |
| 2609 » else if (tpoint->type == static_tracepoint) |
| 2610 » » tpoint->handle = (void *) -1; |
| 2611 » } |
| 2612 » } |
| 2613 |
| 2614 if (use_agent && tpoint->type == fast_tracepoint |
| 2615 » && agent_capability_check (AGENT_CAPA_FAST_TRACE)) |
| 2616 » { |
| 2617 » /* Download and install fast tracepoint by agent. */ |
| 2618 » if (tracepoint_send_agent (tpoint) == 0) |
| 2619 » write_ok (own_buf); |
| 2620 » else |
| 2621 » { |
| 2622 » write_enn (own_buf); |
| 2623 » remove_tracepoint (tpoint); |
| 2624 » } |
| 2625 » } |
| 2626 else |
| 2627 » { |
| 2628 » download_tracepoint (tpoint); |
| 2629 |
| 2630 » if (tpoint->type == trap_tracepoint || tp == NULL) |
| 2631 » { |
| 2632 » install_tracepoint (tpoint, own_buf); |
| 2633 » if (strcmp (own_buf, "OK") != 0) |
| 2634 » » remove_tracepoint (tpoint); |
| 2635 » } |
| 2636 » else |
| 2637 » write_ok (own_buf); |
| 2638 » } |
2458 | 2639 |
2459 unpause_all (1); | 2640 unpause_all (1); |
2460 return; | 2641 return; |
2461 } | 2642 } |
2462 | 2643 |
2463 write_ok (own_buf); | 2644 write_ok (own_buf); |
2464 } | 2645 } |
2465 | 2646 |
2466 static void | 2647 static void |
2467 cmd_qtdpsrc (char *own_buf) | 2648 cmd_qtdpsrc (char *own_buf) |
(...skipping 366 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2834 | 3015 |
2835 /* Ask the IPA to probe the marker at ADDRESS. Returns -1 if running | 3016 /* Ask the IPA to probe the marker at ADDRESS. Returns -1 if running |
2836 the command fails, or 0 otherwise. If the command ran | 3017 the command fails, or 0 otherwise. If the command ran |
2837 successfully, but probing the marker failed, ERROUT will be filled | 3018 successfully, but probing the marker failed, ERROUT will be filled |
2838 with the error to reply to GDB, and -1 is also returned. This | 3019 with the error to reply to GDB, and -1 is also returned. This |
2839 allows directly passing IPA errors to GDB. */ | 3020 allows directly passing IPA errors to GDB. */ |
2840 | 3021 |
2841 static int | 3022 static int |
2842 probe_marker_at (CORE_ADDR address, char *errout) | 3023 probe_marker_at (CORE_ADDR address, char *errout) |
2843 { | 3024 { |
2844 char cmd[CMD_BUF_SIZE]; | 3025 char cmd[IPA_CMD_BUF_SIZE]; |
2845 int err; | 3026 int err; |
2846 | 3027 |
2847 sprintf (cmd, "probe_marker_at:%s", paddress (address)); | 3028 sprintf (cmd, "probe_marker_at:%s", paddress (address)); |
2848 err = run_inferior_command (cmd); | 3029 err = run_inferior_command (cmd, strlen (cmd) + 1); |
2849 | 3030 |
2850 if (err == 0) | 3031 if (err == 0) |
2851 { | 3032 { |
2852 if (*cmd == 'E') | 3033 if (*cmd == 'E') |
2853 { | 3034 { |
2854 strcpy (errout, cmd); | 3035 strcpy (errout, cmd); |
2855 return -1; | 3036 return -1; |
2856 } | 3037 } |
2857 } | 3038 } |
2858 | 3039 |
(...skipping 92 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2951 { | 3132 { |
2952 /* Tracepoints are installed as memory breakpoints. Just go | 3133 /* Tracepoints are installed as memory breakpoints. Just go |
2953 ahead and install the trap. The breakpoints module | 3134 ahead and install the trap. The breakpoints module |
2954 handles duplicated breakpoints, and the memory read | 3135 handles duplicated breakpoints, and the memory read |
2955 routine handles un-patching traps from memory reads. */ | 3136 routine handles un-patching traps from memory reads. */ |
2956 tpoint->handle = set_breakpoint_at (tpoint->address, | 3137 tpoint->handle = set_breakpoint_at (tpoint->address, |
2957 tracepoint_handler); | 3138 tracepoint_handler); |
2958 } | 3139 } |
2959 else if (tpoint->type == fast_tracepoint || tpoint->type == static_tracepoint) | 3140 else if (tpoint->type == fast_tracepoint || tpoint->type == static_tracepoint) |
2960 { | 3141 { |
2961 struct tracepoint *tp; | 3142 if (!agent_loaded_p ()) |
2962 | |
2963 if (!in_process_agent_loaded ()) | |
2964 { | 3143 { |
2965 trace_debug ("Requested a %s tracepoint, but fast " | 3144 trace_debug ("Requested a %s tracepoint, but fast " |
2966 "tracepoints aren't supported.", | 3145 "tracepoints aren't supported.", |
2967 tpoint->type == static_tracepoint ? "static" : "fast"); | 3146 tpoint->type == static_tracepoint ? "static" : "fast"); |
2968 write_e_ipa_not_loaded (own_buf); | 3147 write_e_ipa_not_loaded (own_buf); |
2969 return; | 3148 return; |
2970 } | 3149 } |
2971 if (tpoint->type == static_tracepoint && !in_process_agent_loaded_ust ()) | 3150 if (tpoint->type == static_tracepoint |
| 3151 » && !in_process_agent_supports_ust ()) |
2972 { | 3152 { |
2973 trace_debug ("Requested a static tracepoint, but static " | 3153 trace_debug ("Requested a static tracepoint, but static " |
2974 "tracepoints are not supported."); | 3154 "tracepoints are not supported."); |
2975 write_e_ust_not_loaded (own_buf); | 3155 write_e_ust_not_loaded (own_buf); |
2976 return; | 3156 return; |
2977 } | 3157 } |
2978 | 3158 |
2979 /* Find another fast or static tracepoint at the same address. */ | |
2980 for (tp = tracepoints; tp; tp = tp->next) | |
2981 { | |
2982 if (tp->address == tpoint->address && tp->type == tpoint->type | |
2983 && tp->number != tpoint->number) | |
2984 break; | |
2985 } | |
2986 | |
2987 if (tpoint->type == fast_tracepoint) | 3159 if (tpoint->type == fast_tracepoint) |
2988 » { | 3160 » install_fast_tracepoint (tpoint, own_buf); |
2989 » if (tp) /* TPOINT is installed at the same address as TP. */ | |
2990 » clone_fast_tracepoint (tpoint, tp); | |
2991 » else | |
2992 » install_fast_tracepoint (tpoint, own_buf); | |
2993 » } | |
2994 else | 3161 else |
2995 { | 3162 { |
2996 » if (tp) | 3163 » if (probe_marker_at (tpoint->address, own_buf) == 0) |
2997 tpoint->handle = (void *) -1; | 3164 tpoint->handle = (void *) -1; |
2998 else | |
2999 { | |
3000 if (probe_marker_at (tpoint->address, own_buf) == 0) | |
3001 tpoint->handle = (void *) -1; | |
3002 } | |
3003 } | 3165 } |
3004 | 3166 |
3005 } | 3167 } |
3006 else | 3168 else |
3007 internal_error (__FILE__, __LINE__, "Unknown tracepoint type"); | 3169 internal_error (__FILE__, __LINE__, "Unknown tracepoint type"); |
3008 | 3170 |
3009 if (tpoint->handle == NULL) | 3171 if (tpoint->handle == NULL) |
3010 { | 3172 { |
3011 if (*own_buf == '\0') | 3173 if (*own_buf == '\0') |
3012 write_enn (own_buf); | 3174 write_enn (own_buf); |
3013 } | 3175 } |
3014 else | 3176 else |
3015 write_ok (own_buf); | 3177 write_ok (own_buf); |
3016 } | 3178 } |
3017 | 3179 |
| 3180 static void download_tracepoint_1 (struct tracepoint *tpoint); |
| 3181 |
3018 static void | 3182 static void |
3019 cmd_qtstart (char *packet) | 3183 cmd_qtstart (char *packet) |
3020 { | 3184 { |
3021 struct tracepoint *tpoint, *prev_ftpoint, *prev_stpoint; | 3185 struct tracepoint *tpoint, *prev_ftpoint, *prev_stpoint; |
| 3186 CORE_ADDR tpptr = 0, prev_tpptr = 0; |
3022 | 3187 |
3023 trace_debug ("Starting the trace"); | 3188 trace_debug ("Starting the trace"); |
3024 | 3189 |
3025 /* Pause all threads temporarily while we patch tracepoints. */ | 3190 /* Pause all threads temporarily while we patch tracepoints. */ |
3026 pause_all (0); | 3191 pause_all (0); |
3027 | 3192 |
3028 /* Get threads out of jump pads. Safe to do here, since this is a | 3193 /* Get threads out of jump pads. Safe to do here, since this is a |
3029 top level command. And, required to do here, since we're | 3194 top level command. And, required to do here, since we're |
3030 deleting/rewriting jump pads. */ | 3195 deleting/rewriting jump pads. */ |
3031 | 3196 |
3032 stabilize_threads (); | 3197 stabilize_threads (); |
3033 | 3198 |
3034 /* Freeze threads. */ | 3199 /* Freeze threads. */ |
3035 pause_all (1); | 3200 pause_all (1); |
3036 | 3201 |
3037 /* Sync the fast tracepoints list in the inferior ftlib. */ | 3202 /* Sync the fast tracepoints list in the inferior ftlib. */ |
3038 if (in_process_agent_loaded ()) | 3203 if (agent_loaded_p ()) |
3039 { | 3204 download_trace_state_variables (); |
3040 download_tracepoints (); | |
3041 download_trace_state_variables (); | |
3042 } | |
3043 | 3205 |
3044 /* No previous fast tpoint yet. */ | 3206 /* No previous fast tpoint yet. */ |
3045 prev_ftpoint = NULL; | 3207 prev_ftpoint = NULL; |
3046 | 3208 |
3047 /* No previous static tpoint yet. */ | 3209 /* No previous static tpoint yet. */ |
3048 prev_stpoint = NULL; | 3210 prev_stpoint = NULL; |
3049 | 3211 |
3050 *packet = '\0'; | 3212 *packet = '\0'; |
3051 | 3213 |
3052 /* Install tracepoints. */ | 3214 /* Start out empty. */ |
| 3215 if (agent_loaded_p ()) |
| 3216 write_inferior_data_ptr (ipa_sym_addrs.addr_tracepoints, 0); |
| 3217 |
| 3218 /* Download and install tracepoints. */ |
3053 for (tpoint = tracepoints; tpoint; tpoint = tpoint->next) | 3219 for (tpoint = tracepoints; tpoint; tpoint = tpoint->next) |
3054 { | 3220 { |
3055 /* Ensure all the hit counts start at zero. */ | 3221 /* Ensure all the hit counts start at zero. */ |
3056 tpoint->hit_count = 0; | 3222 tpoint->hit_count = 0; |
3057 tpoint->traceframe_usage = 0; | 3223 tpoint->traceframe_usage = 0; |
3058 | 3224 |
3059 if (tpoint->type == trap_tracepoint) | 3225 if (tpoint->type == trap_tracepoint) |
3060 { | 3226 { |
3061 /* Tracepoints are installed as memory breakpoints. Just go | 3227 /* Tracepoints are installed as memory breakpoints. Just go |
3062 ahead and install the trap. The breakpoints module | 3228 ahead and install the trap. The breakpoints module |
3063 handles duplicated breakpoints, and the memory read | 3229 handles duplicated breakpoints, and the memory read |
3064 routine handles un-patching traps from memory reads. */ | 3230 routine handles un-patching traps from memory reads. */ |
3065 tpoint->handle = set_breakpoint_at (tpoint->address, | 3231 tpoint->handle = set_breakpoint_at (tpoint->address, |
3066 tracepoint_handler); | 3232 tracepoint_handler); |
3067 } | 3233 } |
3068 else if (tpoint->type == fast_tracepoint) | 3234 else if (tpoint->type == fast_tracepoint |
| 3235 » || tpoint->type == static_tracepoint) |
3069 { | 3236 { |
3070 if (maybe_write_ipa_not_loaded (packet)) | 3237 if (maybe_write_ipa_not_loaded (packet)) |
3071 { | 3238 { |
3072 » trace_debug ("Requested a fast tracepoint, but fast " | 3239 » trace_debug ("Requested a %s tracepoint, but fast " |
3073 » » » "tracepoints aren't supported."); | 3240 » » » "tracepoints aren't supported.", |
| 3241 » » » tpoint->type == static_tracepoint |
| 3242 » » » ? "static" : "fast"); |
3074 break; | 3243 break; |
3075 } | 3244 } |
3076 | 3245 |
3077 » if (prev_ftpoint != NULL && prev_ftpoint->address == tpoint->address) | 3246 » if (tpoint->type == fast_tracepoint) |
3078 » clone_fast_tracepoint (tpoint, prev_ftpoint); | |
3079 » else | |
3080 { | 3247 { |
3081 » if (install_fast_tracepoint (tpoint, packet) == 0) | 3248 » int use_agent_p |
3082 » » prev_ftpoint = tpoint; | 3249 » » = use_agent && agent_capability_check (AGENT_CAPA_FAST_TRACE); |
3083 » } | |
3084 » } | |
3085 else if (tpoint->type == static_tracepoint) | |
3086 » { | |
3087 » if (maybe_write_ipa_ust_not_loaded (packet)) | |
3088 » { | |
3089 » trace_debug ("Requested a static tracepoint, but static " | |
3090 » » » "tracepoints are not supported."); | |
3091 » break; | |
3092 » } | |
3093 | 3250 |
3094 » /* Can only probe a given marker once. */ | 3251 » if (prev_ftpoint != NULL |
3095 » if (prev_stpoint != NULL && prev_stpoint->address == tpoint->address) | 3252 » » && prev_ftpoint->address == tpoint->address) |
3096 » { | 3253 » » { |
3097 » tpoint->handle = (void *) -1; | 3254 » » if (use_agent_p) |
| 3255 » » tracepoint_send_agent (tpoint); |
| 3256 » » else |
| 3257 » » download_tracepoint_1 (tpoint); |
| 3258 |
| 3259 » » clone_fast_tracepoint (tpoint, prev_ftpoint); |
| 3260 » » } |
| 3261 » else |
| 3262 » » { |
| 3263 » » /* Tracepoint is installed successfully? */ |
| 3264 » » int installed = 0; |
| 3265 |
| 3266 » » /* Download and install fast tracepoint by agent. */ |
| 3267 » » if (use_agent_p) |
| 3268 » » installed = !tracepoint_send_agent (tpoint); |
| 3269 » » else |
| 3270 » » { |
| 3271 » » download_tracepoint_1 (tpoint); |
| 3272 » » installed = !install_fast_tracepoint (tpoint, packet); |
| 3273 » » } |
| 3274 |
| 3275 » » if (installed) |
| 3276 » » prev_ftpoint = tpoint; |
| 3277 » » } |
3098 } | 3278 } |
3099 else | 3279 else |
3100 { | 3280 { |
3101 » if (probe_marker_at (tpoint->address, packet) == 0) | 3281 » if (!in_process_agent_supports_ust ()) |
3102 { | 3282 { |
3103 » » tpoint->handle = (void *) -1; | 3283 » » trace_debug ("Requested a static tracepoint, but static " |
| 3284 » » » "tracepoints are not supported."); |
| 3285 » » break; |
| 3286 » » } |
3104 | 3287 |
3105 » » /* So that we can handle multiple static tracepoints | 3288 » download_tracepoint_1 (tpoint); |
3106 » » at the same address easily. */ | 3289 » /* Can only probe a given marker once. */ |
3107 » » prev_stpoint = tpoint; | 3290 » if (prev_stpoint != NULL |
| 3291 » » && prev_stpoint->address == tpoint->address) |
| 3292 » » tpoint->handle = (void *) -1; |
| 3293 » else |
| 3294 » » { |
| 3295 » » if (probe_marker_at (tpoint->address, packet) == 0) |
| 3296 » » { |
| 3297 » » tpoint->handle = (void *) -1; |
| 3298 |
| 3299 » » /* So that we can handle multiple static tracepoints |
| 3300 » » » at the same address easily. */ |
| 3301 » » prev_stpoint = tpoint; |
| 3302 » » } |
3108 } | 3303 } |
3109 } | 3304 } |
| 3305 |
| 3306 prev_tpptr = tpptr; |
| 3307 tpptr = tpoint->obj_addr_on_target; |
| 3308 |
| 3309 if (tpoint == tracepoints) |
| 3310 /* First object in list, set the head pointer in the |
| 3311 inferior. */ |
| 3312 write_inferior_data_ptr (ipa_sym_addrs.addr_tracepoints, tpptr); |
| 3313 else |
| 3314 write_inferior_data_ptr (prev_tpptr + offsetof (struct tracepoint, |
| 3315 next), |
| 3316 tpptr); |
3110 } | 3317 } |
3111 | 3318 |
3112 /* Any failure in the inner loop is sufficient cause to give | 3319 /* Any failure in the inner loop is sufficient cause to give |
3113 up. */ | 3320 up. */ |
3114 if (tpoint->handle == NULL) | 3321 if (tpoint->handle == NULL) |
3115 break; | 3322 break; |
3116 } | 3323 } |
3117 | 3324 |
3118 /* Any error in tracepoint insertion is unacceptable; better to | 3325 /* Any error in tracepoint insertion is unacceptable; better to |
3119 address the problem now, than end up with a useless or misleading | 3326 address the problem now, than end up with a useless or misleading |
3120 trace run. */ | 3327 trace run. */ |
3121 if (tpoint != NULL) | 3328 if (tpoint != NULL) |
3122 { | 3329 { |
3123 clear_installed_tracepoints (); | 3330 clear_installed_tracepoints (); |
3124 if (*packet == '\0') | 3331 if (*packet == '\0') |
3125 write_enn (packet); | 3332 write_enn (packet); |
3126 unpause_all (1); | 3333 unpause_all (1); |
3127 return; | 3334 return; |
3128 } | 3335 } |
3129 | 3336 |
3130 stopping_tracepoint = NULL; | 3337 stopping_tracepoint = NULL; |
3131 trace_buffer_is_full = 0; | 3338 trace_buffer_is_full = 0; |
3132 expr_eval_result = expr_eval_no_error; | 3339 expr_eval_result = expr_eval_no_error; |
3133 error_tracepoint = NULL; | 3340 error_tracepoint = NULL; |
3134 tracing_start_time = get_timestamp (); | 3341 tracing_start_time = get_timestamp (); |
3135 | 3342 |
3136 /* Tracing is now active, hits will now start being logged. */ | 3343 /* Tracing is now active, hits will now start being logged. */ |
3137 tracing = 1; | 3344 tracing = 1; |
3138 | 3345 |
3139 if (in_process_agent_loaded ()) | 3346 if (agent_loaded_p ()) |
3140 { | 3347 { |
3141 if (write_inferior_integer (ipa_sym_addrs.addr_tracing, 1)) | 3348 if (write_inferior_integer (ipa_sym_addrs.addr_tracing, 1)) |
3142 fatal ("Error setting tracing variable in lib"); | 3349 fatal ("Error setting tracing variable in lib"); |
3143 | 3350 |
3144 if (write_inferior_data_pointer (ipa_sym_addrs.addr_stopping_tracepoint, | 3351 if (write_inferior_data_pointer (ipa_sym_addrs.addr_stopping_tracepoint, |
3145 0)) | 3352 0)) |
3146 fatal ("Error clearing stopping_tracepoint variable in lib"); | 3353 fatal ("Error clearing stopping_tracepoint variable in lib"); |
3147 | 3354 |
3148 if (write_inferior_integer (ipa_sym_addrs.addr_trace_buffer_is_full, 0)) | 3355 if (write_inferior_integer (ipa_sym_addrs.addr_trace_buffer_is_full, 0)) |
3149 fatal ("Error clearing trace_buffer_is_full variable in lib"); | 3356 fatal ("Error clearing trace_buffer_is_full variable in lib"); |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3188 We can't now, since we may be getting here due to the inferior | 3395 We can't now, since we may be getting here due to the inferior |
3189 agent calling us. */ | 3396 agent calling us. */ |
3190 pause_all (1); | 3397 pause_all (1); |
3191 /* Since we're removing breakpoints, cancel breakpoint hits, | 3398 /* Since we're removing breakpoints, cancel breakpoint hits, |
3192 possibly related to the breakpoints we're about to delete. */ | 3399 possibly related to the breakpoints we're about to delete. */ |
3193 cancel_breakpoints (); | 3400 cancel_breakpoints (); |
3194 | 3401 |
3195 /* Stop logging. Tracepoints can still be hit, but they will not be | 3402 /* Stop logging. Tracepoints can still be hit, but they will not be |
3196 recorded. */ | 3403 recorded. */ |
3197 tracing = 0; | 3404 tracing = 0; |
3198 if (in_process_agent_loaded ()) | 3405 if (agent_loaded_p ()) |
3199 { | 3406 { |
3200 if (write_inferior_integer (ipa_sym_addrs.addr_tracing, 0)) | 3407 if (write_inferior_integer (ipa_sym_addrs.addr_tracing, 0)) |
3201 fatal ("Error clearing tracing variable in lib"); | 3408 fatal ("Error clearing tracing variable in lib"); |
3202 } | 3409 } |
3203 | 3410 |
3204 tracing_stop_time = get_timestamp (); | 3411 tracing_stop_time = get_timestamp (); |
3205 tracing_stop_reason = "t???"; | 3412 tracing_stop_reason = "t???"; |
3206 tracing_stop_tpnum = 0; | 3413 tracing_stop_tpnum = 0; |
3207 if (stopping_tracepoint) | 3414 if (stopping_tracepoint) |
3208 { | 3415 { |
3209 trace_debug ("Stopping the trace because " | 3416 trace_debug ("Stopping the trace because " |
3210 » » "tracepoint %d was hit %ld times", | 3417 » » "tracepoint %d was hit %" PRIu64 " times", |
3211 stopping_tracepoint->number, | 3418 stopping_tracepoint->number, |
3212 stopping_tracepoint->pass_count); | 3419 stopping_tracepoint->pass_count); |
3213 tracing_stop_reason = "tpasscount"; | 3420 tracing_stop_reason = "tpasscount"; |
3214 tracing_stop_tpnum = stopping_tracepoint->number; | 3421 tracing_stop_tpnum = stopping_tracepoint->number; |
3215 } | 3422 } |
3216 else if (trace_buffer_is_full) | 3423 else if (trace_buffer_is_full) |
3217 { | 3424 { |
3218 trace_debug ("Stopping the trace because the trace buffer is full"); | 3425 trace_debug ("Stopping the trace because the trace buffer is full"); |
3219 tracing_stop_reason = "tfull"; | 3426 tracing_stop_reason = "tfull"; |
3220 } | 3427 } |
(...skipping 15 matching lines...) Expand all Loading... |
3236 trace_debug ("Stopping the trace because of a tstop command"); | 3443 trace_debug ("Stopping the trace because of a tstop command"); |
3237 tracing_stop_reason = "tstop"; | 3444 tracing_stop_reason = "tstop"; |
3238 } | 3445 } |
3239 | 3446 |
3240 stopping_tracepoint = NULL; | 3447 stopping_tracepoint = NULL; |
3241 error_tracepoint = NULL; | 3448 error_tracepoint = NULL; |
3242 | 3449 |
3243 /* Clear out the tracepoints. */ | 3450 /* Clear out the tracepoints. */ |
3244 clear_installed_tracepoints (); | 3451 clear_installed_tracepoints (); |
3245 | 3452 |
3246 if (in_process_agent_loaded ()) | 3453 if (agent_loaded_p ()) |
3247 { | 3454 { |
3248 /* Pull in fast tracepoint trace frames from the inferior lib | 3455 /* Pull in fast tracepoint trace frames from the inferior lib |
3249 buffer into our buffer, even if our buffer is already full, | 3456 buffer into our buffer, even if our buffer is already full, |
3250 because we want to present the full number of created frames | 3457 because we want to present the full number of created frames |
3251 in addition to what fit in the trace buffer. */ | 3458 in addition to what fit in the trace buffer. */ |
3252 upload_fast_traceframes (); | 3459 upload_fast_traceframes (); |
3253 } | 3460 } |
3254 | 3461 |
3255 if (stop_tracing_bkpt != NULL) | 3462 if (stop_tracing_bkpt != NULL) |
3256 { | 3463 { |
(...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3399 hexify (buf2, str, slen); | 3606 hexify (buf2, str, slen); |
3400 | 3607 |
3401 str = (tracing_stop_note ? tracing_stop_note : ""); | 3608 str = (tracing_stop_note ? tracing_stop_note : ""); |
3402 slen = strlen (str); | 3609 slen = strlen (str); |
3403 buf3 = (char *) alloca (slen * 2 + 1); | 3610 buf3 = (char *) alloca (slen * 2 + 1); |
3404 hexify (buf3, str, slen); | 3611 hexify (buf3, str, slen); |
3405 | 3612 |
3406 trace_debug ("Returning trace status as %d, stop reason %s", | 3613 trace_debug ("Returning trace status as %d, stop reason %s", |
3407 tracing, tracing_stop_reason); | 3614 tracing, tracing_stop_reason); |
3408 | 3615 |
3409 if (in_process_agent_loaded ()) | 3616 if (agent_loaded_p ()) |
3410 { | 3617 { |
3411 pause_all (1); | 3618 pause_all (1); |
3412 | 3619 |
3413 upload_fast_traceframes (); | 3620 upload_fast_traceframes (); |
3414 | 3621 |
3415 unpause_all (1); | 3622 unpause_all (1); |
3416 } | 3623 } |
3417 | 3624 |
3418 stop_reason_rsp = (char *) tracing_stop_reason; | 3625 stop_reason_rsp = (char *) tracing_stop_reason; |
3419 | 3626 |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3478 tpoint = find_tracepoint (num, addr); | 3685 tpoint = find_tracepoint (num, addr); |
3479 | 3686 |
3480 if (!tpoint) | 3687 if (!tpoint) |
3481 { | 3688 { |
3482 trace_debug ("Tracepoint error: tracepoint %d at 0x%s not found", | 3689 trace_debug ("Tracepoint error: tracepoint %d at 0x%s not found", |
3483 (int) num, paddress (addr)); | 3690 (int) num, paddress (addr)); |
3484 write_enn (own_buf); | 3691 write_enn (own_buf); |
3485 return; | 3692 return; |
3486 } | 3693 } |
3487 | 3694 |
3488 sprintf (own_buf, "V%lx:%lx", tpoint->hit_count, tpoint->traceframe_usage); | 3695 sprintf (own_buf, "V%" PRIu64 ":%" PRIu64 "", tpoint->hit_count, |
| 3696 » tpoint->traceframe_usage); |
3489 } | 3697 } |
3490 | 3698 |
3491 /* State variables to help return all the tracepoint bits. */ | 3699 /* State variables to help return all the tracepoint bits. */ |
3492 static struct tracepoint *cur_tpoint; | 3700 static struct tracepoint *cur_tpoint; |
3493 static int cur_action; | 3701 static int cur_action; |
3494 static int cur_step_action; | 3702 static int cur_step_action; |
3495 static struct source_string *cur_source_string; | 3703 static struct source_string *cur_source_string; |
3496 static struct trace_state_variable *cur_tsv; | 3704 static struct trace_state_variable *cur_tsv; |
3497 | 3705 |
3498 /* Compose a response that is an imitation of the syntax by which the | 3706 /* Compose a response that is an imitation of the syntax by which the |
3499 tracepoint was originally downloaded. */ | 3707 tracepoint was originally downloaded. */ |
3500 | 3708 |
3501 static void | 3709 static void |
3502 response_tracepoint (char *packet, struct tracepoint *tpoint) | 3710 response_tracepoint (char *packet, struct tracepoint *tpoint) |
3503 { | 3711 { |
3504 char *buf; | 3712 char *buf; |
3505 | 3713 |
3506 sprintf (packet, "T%x:%s:%c:%lx:%lx", tpoint->number, | 3714 sprintf (packet, "T%x:%s:%c:%" PRIx64 ":%" PRIx64, tpoint->number, |
3507 paddress (tpoint->address), | 3715 paddress (tpoint->address), |
3508 (tpoint->enabled ? 'E' : 'D'), tpoint->step_count, | 3716 (tpoint->enabled ? 'E' : 'D'), tpoint->step_count, |
3509 tpoint->pass_count); | 3717 tpoint->pass_count); |
3510 if (tpoint->type == fast_tracepoint) | 3718 if (tpoint->type == fast_tracepoint) |
3511 sprintf (packet + strlen (packet), ":F%x", tpoint->orig_size); | 3719 sprintf (packet + strlen (packet), ":F%x", tpoint->orig_size); |
3512 else if (tpoint->type == static_tracepoint) | 3720 else if (tpoint->type == static_tracepoint) |
3513 sprintf (packet + strlen (packet), ":S"); | 3721 sprintf (packet + strlen (packet), ":S"); |
3514 | 3722 |
3515 if (tpoint->cond) | 3723 if (tpoint->cond) |
3516 { | 3724 { |
3517 buf = unparse_agent_expr (tpoint->cond); | 3725 buf = gdb_unparse_agent_expr (tpoint->cond); |
3518 sprintf (packet + strlen (packet), ":X%x,%s", | 3726 sprintf (packet + strlen (packet), ":X%x,%s", |
3519 tpoint->cond->length, buf); | 3727 tpoint->cond->length, buf); |
3520 free (buf); | 3728 free (buf); |
3521 } | 3729 } |
3522 } | 3730 } |
3523 | 3731 |
3524 /* Compose a response that is an imitation of the syntax by which the | 3732 /* Compose a response that is an imitation of the syntax by which the |
3525 tracepoint action was originally downloaded (with the difference | 3733 tracepoint action was originally downloaded (with the difference |
3526 that due to the way we store the actions, this will output a packet | 3734 that due to the way we store the actions, this will output a packet |
3527 per action, while GDB could have combined more than one action | 3735 per action, while GDB could have combined more than one action |
(...skipping 158 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3686 } | 3894 } |
3687 | 3895 |
3688 /* Return the first static tracepoint marker, and initialize the state | 3896 /* Return the first static tracepoint marker, and initialize the state |
3689 machine that will iterate through all the static tracepoints | 3897 machine that will iterate through all the static tracepoints |
3690 markers. */ | 3898 markers. */ |
3691 | 3899 |
3692 static void | 3900 static void |
3693 cmd_qtfstm (char *packet) | 3901 cmd_qtfstm (char *packet) |
3694 { | 3902 { |
3695 if (!maybe_write_ipa_ust_not_loaded (packet)) | 3903 if (!maybe_write_ipa_ust_not_loaded (packet)) |
3696 run_inferior_command (packet); | 3904 run_inferior_command (packet, strlen (packet) + 1); |
3697 } | 3905 } |
3698 | 3906 |
3699 /* Return additional static tracepoints markers. */ | 3907 /* Return additional static tracepoints markers. */ |
3700 | 3908 |
3701 static void | 3909 static void |
3702 cmd_qtsstm (char *packet) | 3910 cmd_qtsstm (char *packet) |
3703 { | 3911 { |
3704 if (!maybe_write_ipa_ust_not_loaded (packet)) | 3912 if (!maybe_write_ipa_ust_not_loaded (packet)) |
3705 run_inferior_command (packet); | 3913 run_inferior_command (packet, strlen (packet) + 1); |
3706 } | 3914 } |
3707 | 3915 |
3708 /* Return the definition of the static tracepoint at a given address. | 3916 /* Return the definition of the static tracepoint at a given address. |
3709 Result packet is the same as qTsST's. */ | 3917 Result packet is the same as qTsST's. */ |
3710 | 3918 |
3711 static void | 3919 static void |
3712 cmd_qtstmat (char *packet) | 3920 cmd_qtstmat (char *packet) |
3713 { | 3921 { |
3714 if (!maybe_write_ipa_ust_not_loaded (packet)) | 3922 if (!maybe_write_ipa_ust_not_loaded (packet)) |
3715 run_inferior_command (packet); | 3923 run_inferior_command (packet, strlen (packet) + 1); |
3716 } | 3924 } |
3717 | 3925 |
3718 /* Return the minimum instruction size needed for fast tracepoints as a | 3926 /* Return the minimum instruction size needed for fast tracepoints as a |
3719 hexadecimal number. */ | 3927 hexadecimal number. */ |
3720 | 3928 |
3721 static void | 3929 static void |
3722 cmd_qtminftpilen (char *packet) | 3930 cmd_qtminftpilen (char *packet) |
3723 { | 3931 { |
| 3932 if (current_inferior == NULL) |
| 3933 { |
| 3934 /* Indicate that the minimum length is currently unknown. */ |
| 3935 strcpy (packet, "0"); |
| 3936 return; |
| 3937 } |
| 3938 |
3724 sprintf (packet, "%x", target_get_min_fast_tracepoint_insn_len ()); | 3939 sprintf (packet, "%x", target_get_min_fast_tracepoint_insn_len ()); |
3725 } | 3940 } |
3726 | 3941 |
3727 /* Respond to qTBuffer packet with a block of raw data from the trace | 3942 /* Respond to qTBuffer packet with a block of raw data from the trace |
3728 buffer. GDB may ask for a lot, but we are allowed to reply with | 3943 buffer. GDB may ask for a lot, but we are allowed to reply with |
3729 only as much as will fit within packet limits or whatever. */ | 3944 only as much as will fit within packet limits or whatever. */ |
3730 | 3945 |
3731 static void | 3946 static void |
3732 cmd_qtbuffer (char *own_buf) | 3947 cmd_qtbuffer (char *own_buf) |
3733 { | 3948 { |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3772 | 3987 |
3773 /* Trim to available packet size. */ | 3988 /* Trim to available packet size. */ |
3774 if (num >= (PBUFSIZ - 16) / 2 ) | 3989 if (num >= (PBUFSIZ - 16) / 2 ) |
3775 num = (PBUFSIZ - 16) / 2; | 3990 num = (PBUFSIZ - 16) / 2; |
3776 | 3991 |
3777 convert_int_to_ascii (tbp, own_buf, num); | 3992 convert_int_to_ascii (tbp, own_buf, num); |
3778 own_buf[num] = '\0'; | 3993 own_buf[num] = '\0'; |
3779 } | 3994 } |
3780 | 3995 |
3781 static void | 3996 static void |
3782 cmd_bigqtbuffer (char *own_buf) | 3997 cmd_bigqtbuffer_circular (char *own_buf) |
3783 { | 3998 { |
3784 ULONGEST val; | 3999 ULONGEST val; |
3785 char *packet = own_buf; | 4000 char *packet = own_buf; |
3786 | 4001 |
3787 packet += strlen ("QTBuffer:"); | 4002 packet += strlen ("QTBuffer:circular:"); |
3788 | 4003 |
3789 if (strncmp ("circular:", packet, strlen ("circular:")) == 0) | 4004 unpack_varlen_hex (packet, &val); |
3790 { | 4005 circular_trace_buffer = val; |
3791 packet += strlen ("circular:"); | 4006 trace_debug ("Trace buffer is now %s", |
3792 unpack_varlen_hex (packet, &val); | 4007 » circular_trace_buffer ? "circular" : "linear"); |
3793 circular_trace_buffer = val; | 4008 write_ok (own_buf); |
3794 trace_debug ("Trace buffer is now %s", | |
3795 » » circular_trace_buffer ? "circular" : "linear"); | |
3796 write_ok (own_buf); | |
3797 } | |
3798 else | |
3799 write_enn (own_buf); | |
3800 } | 4009 } |
3801 | 4010 |
3802 static void | 4011 static void |
3803 cmd_qtnotes (char *own_buf) | 4012 cmd_qtnotes (char *own_buf) |
3804 { | 4013 { |
3805 size_t nbytes; | 4014 size_t nbytes; |
3806 char *saved, *user, *notes, *stopnote; | 4015 char *saved, *user, *notes, *stopnote; |
3807 char *packet = own_buf; | 4016 char *packet = own_buf; |
3808 | 4017 |
3809 packet += strlen ("QTNotes:"); | 4018 packet += strlen ("QTNotes:"); |
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3908 strlen ("QTDisconnected:")) == 0) | 4117 strlen ("QTDisconnected:")) == 0) |
3909 { | 4118 { |
3910 cmd_qtdisconnected (packet); | 4119 cmd_qtdisconnected (packet); |
3911 return 1; | 4120 return 1; |
3912 } | 4121 } |
3913 else if (strncmp ("QTFrame:", packet, strlen ("QTFrame:")) == 0) | 4122 else if (strncmp ("QTFrame:", packet, strlen ("QTFrame:")) == 0) |
3914 { | 4123 { |
3915 cmd_qtframe (packet); | 4124 cmd_qtframe (packet); |
3916 return 1; | 4125 return 1; |
3917 } | 4126 } |
3918 else if (strncmp ("QTBuffer:", packet, strlen ("QTBuffer:")) == 0) | 4127 else if (strncmp ("QTBuffer:circular:", packet, strlen ("QTBuffer:circular:"))
== 0) |
3919 { | 4128 { |
3920 cmd_bigqtbuffer (packet); | 4129 cmd_bigqtbuffer_circular (packet); |
3921 return 1; | 4130 return 1; |
3922 } | 4131 } |
3923 else if (strncmp ("QTNotes:", packet, strlen ("QTNotes:")) == 0) | 4132 else if (strncmp ("QTNotes:", packet, strlen ("QTNotes:")) == 0) |
3924 { | 4133 { |
3925 cmd_qtnotes (packet); | 4134 cmd_qtnotes (packet); |
3926 return 1; | 4135 return 1; |
3927 } | 4136 } |
3928 | 4137 |
3929 return 0; | 4138 return 0; |
3930 } | 4139 } |
(...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4066 int | 4275 int |
4067 tracepoint_finished_step (struct thread_info *tinfo, CORE_ADDR stop_pc) | 4276 tracepoint_finished_step (struct thread_info *tinfo, CORE_ADDR stop_pc) |
4068 { | 4277 { |
4069 struct tracepoint *tpoint; | 4278 struct tracepoint *tpoint; |
4070 struct wstep_state *wstep; | 4279 struct wstep_state *wstep; |
4071 struct wstep_state **wstep_link; | 4280 struct wstep_state **wstep_link; |
4072 struct trap_tracepoint_ctx ctx; | 4281 struct trap_tracepoint_ctx ctx; |
4073 | 4282 |
4074 /* Pull in fast tracepoint trace frames from the inferior lib buffer into | 4283 /* Pull in fast tracepoint trace frames from the inferior lib buffer into |
4075 our buffer. */ | 4284 our buffer. */ |
4076 if (in_process_agent_loaded ()) | 4285 if (agent_loaded_p ()) |
4077 upload_fast_traceframes (); | 4286 upload_fast_traceframes (); |
4078 | 4287 |
4079 /* Check if we were indeed collecting data for one of more | 4288 /* Check if we were indeed collecting data for one of more |
4080 tracepoints with a 'while-stepping' count. */ | 4289 tracepoints with a 'while-stepping' count. */ |
4081 if (tinfo->while_stepping == NULL) | 4290 if (tinfo->while_stepping == NULL) |
4082 return 0; | 4291 return 0; |
4083 | 4292 |
4084 if (!tracing) | 4293 if (!tracing) |
4085 { | 4294 { |
4086 /* We're not even tracing anymore. Stop this thread from | 4295 /* We're not even tracing anymore. Stop this thread from |
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4167 /* Handle any internal tracing control breakpoint hits. That means, | 4376 /* Handle any internal tracing control breakpoint hits. That means, |
4168 pull traceframes from the IPA to our buffer, and syncing both | 4377 pull traceframes from the IPA to our buffer, and syncing both |
4169 tracing agents when the IPA's tracing stops for some reason. */ | 4378 tracing agents when the IPA's tracing stops for some reason. */ |
4170 | 4379 |
4171 int | 4380 int |
4172 handle_tracepoint_bkpts (struct thread_info *tinfo, CORE_ADDR stop_pc) | 4381 handle_tracepoint_bkpts (struct thread_info *tinfo, CORE_ADDR stop_pc) |
4173 { | 4382 { |
4174 /* Pull in fast tracepoint trace frames from the inferior in-process | 4383 /* Pull in fast tracepoint trace frames from the inferior in-process |
4175 agent's buffer into our buffer. */ | 4384 agent's buffer into our buffer. */ |
4176 | 4385 |
4177 if (!in_process_agent_loaded ()) | 4386 if (!agent_loaded_p ()) |
4178 return 0; | 4387 return 0; |
4179 | 4388 |
4180 upload_fast_traceframes (); | 4389 upload_fast_traceframes (); |
4181 | 4390 |
4182 /* Check if the in-process agent had decided we should stop | 4391 /* Check if the in-process agent had decided we should stop |
4183 tracing. */ | 4392 tracing. */ |
4184 if (stop_pc == ipa_sym_addrs.addr_stop_tracing) | 4393 if (stop_pc == ipa_sym_addrs.addr_stop_tracing) |
4185 { | 4394 { |
4186 int ipa_trace_buffer_is_full; | 4395 int ipa_trace_buffer_is_full; |
4187 CORE_ADDR ipa_stopping_tracepoint; | 4396 CORE_ADDR ipa_stopping_tracepoint; |
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4261 if (!tracing) | 4470 if (!tracing) |
4262 return 0; | 4471 return 0; |
4263 | 4472 |
4264 ctx.base.type = trap_tracepoint; | 4473 ctx.base.type = trap_tracepoint; |
4265 ctx.regcache = get_thread_regcache (tinfo, 1); | 4474 ctx.regcache = get_thread_regcache (tinfo, 1); |
4266 | 4475 |
4267 for (tpoint = tracepoints; tpoint; tpoint = tpoint->next) | 4476 for (tpoint = tracepoints; tpoint; tpoint = tpoint->next) |
4268 { | 4477 { |
4269 /* Note that we collect fast tracepoints here as well. We'll | 4478 /* Note that we collect fast tracepoints here as well. We'll |
4270 step over the fast tracepoint jump later, which avoids the | 4479 step over the fast tracepoint jump later, which avoids the |
4271 » double collect. */ | 4480 » double collect. However, we don't collect for static |
4272 if (tpoint->enabled && stop_pc == tpoint->address) | 4481 » tracepoints here, because UST markers are compiled in program, |
| 4482 » and probes will be executed in program. So static tracepoints |
| 4483 » are collected there. */ |
| 4484 if (tpoint->enabled && stop_pc == tpoint->address |
| 4485 » && tpoint->type != static_tracepoint) |
4273 { | 4486 { |
4274 trace_debug ("Thread %s at address of tracepoint %d at 0x%s", | 4487 trace_debug ("Thread %s at address of tracepoint %d at 0x%s", |
4275 target_pid_to_str (tinfo->entry.id), | 4488 target_pid_to_str (tinfo->entry.id), |
4276 tpoint->number, paddress (tpoint->address)); | 4489 tpoint->number, paddress (tpoint->address)); |
4277 | 4490 |
4278 /* Test the condition if present, and collect if true. */ | 4491 /* Test the condition if present, and collect if true. */ |
4279 if (!tpoint->cond | 4492 if (!tpoint->cond |
4280 || (condition_true_at_tracepoint | 4493 || (condition_true_at_tracepoint |
4281 ((struct tracepoint_hit_ctx *) &ctx, tpoint))) | 4494 ((struct tracepoint_hit_ctx *) &ctx, tpoint))) |
4282 collect_data_at_tracepoint ((struct tracepoint_hit_ctx *) &ctx, | 4495 collect_data_at_tracepoint ((struct tracepoint_hit_ctx *) &ctx, |
(...skipping 19 matching lines...) Expand all Loading... |
4302 } | 4515 } |
4303 | 4516 |
4304 return ret; | 4517 return ret; |
4305 } | 4518 } |
4306 | 4519 |
4307 #endif | 4520 #endif |
4308 | 4521 |
4309 #if defined IN_PROCESS_AGENT && defined HAVE_UST | 4522 #if defined IN_PROCESS_AGENT && defined HAVE_UST |
4310 struct ust_marker_data; | 4523 struct ust_marker_data; |
4311 static void collect_ust_data_at_tracepoint (struct tracepoint_hit_ctx *ctx, | 4524 static void collect_ust_data_at_tracepoint (struct tracepoint_hit_ctx *ctx, |
4312 CORE_ADDR stop_pc, | |
4313 struct tracepoint *tpoint, | |
4314 struct traceframe *tframe); | 4525 struct traceframe *tframe); |
4315 #endif | 4526 #endif |
4316 | 4527 |
4317 /* Create a trace frame for the hit of the given tracepoint in the | 4528 /* Create a trace frame for the hit of the given tracepoint in the |
4318 given thread. */ | 4529 given thread. */ |
4319 | 4530 |
4320 static void | 4531 static void |
4321 collect_data_at_tracepoint (struct tracepoint_hit_ctx *ctx, CORE_ADDR stop_pc, | 4532 collect_data_at_tracepoint (struct tracepoint_hit_ctx *ctx, CORE_ADDR stop_pc, |
4322 struct tracepoint *tpoint) | 4533 struct tracepoint *tpoint) |
4323 { | 4534 { |
4324 struct traceframe *tframe; | 4535 struct traceframe *tframe; |
4325 int acti; | 4536 int acti; |
4326 | 4537 |
4327 /* Only count it as a hit when we actually collect data. */ | 4538 /* Only count it as a hit when we actually collect data. */ |
4328 tpoint->hit_count++; | 4539 tpoint->hit_count++; |
4329 | 4540 |
4330 /* If we've exceeded a defined pass count, record the event for | 4541 /* If we've exceeded a defined pass count, record the event for |
4331 later, and finish the collection for this hit. This test is only | 4542 later, and finish the collection for this hit. This test is only |
4332 for nonstepping tracepoints, stepping tracepoints test at the end | 4543 for nonstepping tracepoints, stepping tracepoints test at the end |
4333 of their while-stepping loop. */ | 4544 of their while-stepping loop. */ |
4334 if (tpoint->pass_count > 0 | 4545 if (tpoint->pass_count > 0 |
4335 && tpoint->hit_count >= tpoint->pass_count | 4546 && tpoint->hit_count >= tpoint->pass_count |
4336 && tpoint->step_count == 0 | 4547 && tpoint->step_count == 0 |
4337 && stopping_tracepoint == NULL) | 4548 && stopping_tracepoint == NULL) |
4338 stopping_tracepoint = tpoint; | 4549 stopping_tracepoint = tpoint; |
4339 | 4550 |
4340 trace_debug ("Making new traceframe for tracepoint %d at 0x%s, hit %ld", | 4551 trace_debug ("Making new traceframe for tracepoint %d at 0x%s, hit %" PRIu64, |
4341 tpoint->number, paddress (tpoint->address), tpoint->hit_count); | 4552 tpoint->number, paddress (tpoint->address), tpoint->hit_count); |
4342 | 4553 |
4343 tframe = add_traceframe (tpoint); | 4554 tframe = add_traceframe (tpoint); |
4344 | 4555 |
4345 if (tframe) | 4556 if (tframe) |
4346 { | 4557 { |
4347 for (acti = 0; acti < tpoint->numactions; ++acti) | 4558 for (acti = 0; acti < tpoint->numactions; ++acti) |
4348 { | 4559 { |
4349 #ifndef IN_PROCESS_AGENT | 4560 #ifndef IN_PROCESS_AGENT |
4350 trace_debug ("Tracepoint %d at 0x%s about to do action '%s'", | 4561 trace_debug ("Tracepoint %d at 0x%s about to do action '%s'", |
(...skipping 16 matching lines...) Expand all Loading... |
4367 | 4578 |
4368 static void | 4579 static void |
4369 collect_data_at_step (struct tracepoint_hit_ctx *ctx, | 4580 collect_data_at_step (struct tracepoint_hit_ctx *ctx, |
4370 CORE_ADDR stop_pc, | 4581 CORE_ADDR stop_pc, |
4371 struct tracepoint *tpoint, int current_step) | 4582 struct tracepoint *tpoint, int current_step) |
4372 { | 4583 { |
4373 struct traceframe *tframe; | 4584 struct traceframe *tframe; |
4374 int acti; | 4585 int acti; |
4375 | 4586 |
4376 trace_debug ("Making new step traceframe for " | 4587 trace_debug ("Making new step traceframe for " |
4377 » "tracepoint %d at 0x%s, step %d of %ld, hit %ld", | 4588 » "tracepoint %d at 0x%s, step %d of %" PRIu64 ", hit %" PRIu64, |
4378 tpoint->number, paddress (tpoint->address), | 4589 tpoint->number, paddress (tpoint->address), |
4379 current_step, tpoint->step_count, | 4590 current_step, tpoint->step_count, |
4380 tpoint->hit_count); | 4591 tpoint->hit_count); |
4381 | 4592 |
4382 tframe = add_traceframe (tpoint); | 4593 tframe = add_traceframe (tpoint); |
4383 | 4594 |
4384 if (tframe) | 4595 if (tframe) |
4385 { | 4596 { |
4386 for (acti = 0; acti < tpoint->num_step_actions; ++acti) | 4597 for (acti = 0; acti < tpoint->num_step_actions; ++acti) |
4387 { | 4598 { |
(...skipping 125 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4513 pointing to the next instruction after the trap, but we | 4724 pointing to the next instruction after the trap, but we |
4514 don't want the user or GDB trying to guess whether the | 4725 don't want the user or GDB trying to guess whether the |
4515 saved PC needs adjusting; so always record the adjusted | 4726 saved PC needs adjusting; so always record the adjusted |
4516 stop_pc. Note that we can't use tpoint->address instead, | 4727 stop_pc. Note that we can't use tpoint->address instead, |
4517 since it will be wrong for while-stepping actions. This | 4728 since it will be wrong for while-stepping actions. This |
4518 adjustment is a nop for fast tracepoints collected from the | 4729 adjustment is a nop for fast tracepoints collected from the |
4519 in-process lib (but not if GDBserver is collecting one | 4730 in-process lib (but not if GDBserver is collecting one |
4520 preemptively), since the PC had already been adjusted to | 4731 preemptively), since the PC had already been adjusted to |
4521 contain the tracepoint's address by the jump pad. */ | 4732 contain the tracepoint's address by the jump pad. */ |
4522 trace_debug ("Storing stop pc (0x%s) in regblock", | 4733 trace_debug ("Storing stop pc (0x%s) in regblock", |
4523 » » paddress (tpoint->address)); | 4734 » » paddress (stop_pc)); |
4524 | 4735 |
4525 /* This changes the regblock, not the thread's | 4736 /* This changes the regblock, not the thread's |
4526 regcache. */ | 4737 regcache. */ |
4527 regcache_write_pc (&tregcache, stop_pc); | 4738 regcache_write_pc (&tregcache, stop_pc); |
4528 #endif | 4739 #endif |
4529 } | 4740 } |
4530 break; | 4741 break; |
4531 case 'X': | 4742 case 'X': |
4532 { | 4743 { |
4533 struct eval_expr_action *eaction; | 4744 struct eval_expr_action *eaction; |
4534 | 4745 |
4535 eaction = (struct eval_expr_action *) taction; | 4746 eaction = (struct eval_expr_action *) taction; |
4536 | 4747 |
4537 trace_debug ("Want to evaluate expression"); | 4748 trace_debug ("Want to evaluate expression"); |
4538 | 4749 |
4539 » err = eval_agent_expr (ctx, tframe, eaction->expr, NULL); | 4750 » err = eval_tracepoint_agent_expr (ctx, tframe, eaction->expr, NULL); |
4540 | 4751 |
4541 if (err != expr_eval_no_error) | 4752 if (err != expr_eval_no_error) |
4542 { | 4753 { |
4543 record_tracepoint_error (tpoint, "action expression", err); | 4754 record_tracepoint_error (tpoint, "action expression", err); |
4544 return; | 4755 return; |
4545 } | 4756 } |
4546 } | 4757 } |
4547 break; | 4758 break; |
4548 case 'L': | 4759 case 'L': |
4549 { | 4760 { |
4550 #if defined IN_PROCESS_AGENT && defined HAVE_UST | 4761 #if defined IN_PROCESS_AGENT && defined HAVE_UST |
4551 trace_debug ("Want to collect static trace data"); | 4762 trace_debug ("Want to collect static trace data"); |
4552 » collect_ust_data_at_tracepoint (ctx, stop_pc, | 4763 » collect_ust_data_at_tracepoint (ctx, tframe); |
4553 » » » » » tpoint, tframe); | |
4554 #else | 4764 #else |
4555 trace_debug ("warning: collecting static trace data, " | 4765 trace_debug ("warning: collecting static trace data, " |
4556 "but static tracepoints are not supported"); | 4766 "but static tracepoints are not supported"); |
4557 #endif | 4767 #endif |
4558 } | 4768 } |
4559 break; | 4769 break; |
4560 default: | 4770 default: |
4561 trace_debug ("unknown trace action '%c', ignoring", taction->type); | 4771 trace_debug ("unknown trace action '%c', ignoring", taction->type); |
4562 break; | 4772 break; |
4563 } | 4773 } |
(...skipping 18 matching lines...) Expand all Loading... |
4582 tracepoints are collected, compared to an alternative where only | 4792 tracepoints are collected, compared to an alternative where only |
4583 trap tracepoints are collected on stop, and fast tracepoints on | 4793 trap tracepoints are collected on stop, and fast tracepoints on |
4584 resume. When a fast tracepoint is being processed by gdbserver, | 4794 resume. When a fast tracepoint is being processed by gdbserver, |
4585 it is always the non-compiled condition expression that is | 4795 it is always the non-compiled condition expression that is |
4586 used. */ | 4796 used. */ |
4587 #ifdef IN_PROCESS_AGENT | 4797 #ifdef IN_PROCESS_AGENT |
4588 if (tpoint->compiled_cond) | 4798 if (tpoint->compiled_cond) |
4589 err = ((condfn) (uintptr_t) (tpoint->compiled_cond)) (ctx, &value); | 4799 err = ((condfn) (uintptr_t) (tpoint->compiled_cond)) (ctx, &value); |
4590 else | 4800 else |
4591 #endif | 4801 #endif |
4592 err = eval_agent_expr (ctx, NULL, tpoint->cond, &value); | 4802 err = eval_tracepoint_agent_expr (ctx, NULL, tpoint->cond, &value); |
4593 | 4803 |
4594 if (err != expr_eval_no_error) | 4804 if (err != expr_eval_no_error) |
4595 { | 4805 { |
4596 record_tracepoint_error (tpoint, "condition", err); | 4806 record_tracepoint_error (tpoint, "condition", err); |
4597 /* The error case must return false. */ | 4807 /* The error case must return false. */ |
4598 return 0; | 4808 return 0; |
4599 } | 4809 } |
4600 | 4810 |
4601 trace_debug ("Tracepoint %d at 0x%s condition evals to %s", | 4811 trace_debug ("Tracepoint %d at 0x%s condition evals to %s", |
4602 tpoint->number, paddress (tpoint->address), | 4812 tpoint->number, paddress (tpoint->address), |
4603 pulongest (value)); | 4813 pulongest (value)); |
4604 return (value ? 1 : 0); | 4814 return (value ? 1 : 0); |
4605 } | 4815 } |
4606 | 4816 |
4607 #ifndef IN_PROCESS_AGENT | 4817 /* Evaluates a tracepoint agent expression with context CTX, |
4608 | 4818 traceframe TFRAME, agent expression AEXPR and store the |
4609 /* The packet form of an agent expression consists of an 'X', number | 4819 result in RSLT. */ |
4610 of bytes in expression, a comma, and then the bytes. */ | |
4611 | |
4612 static struct agent_expr * | |
4613 parse_agent_expr (char **actparm) | |
4614 { | |
4615 char *act = *actparm; | |
4616 ULONGEST xlen; | |
4617 struct agent_expr *aexpr; | |
4618 | |
4619 ++act; /* skip the X */ | |
4620 act = unpack_varlen_hex (act, &xlen); | |
4621 ++act; /* skip a comma */ | |
4622 aexpr = xmalloc (sizeof (struct agent_expr)); | |
4623 aexpr->length = xlen; | |
4624 aexpr->bytes = xmalloc (xlen); | |
4625 convert_ascii_to_int (act, aexpr->bytes, xlen); | |
4626 *actparm = act + (xlen * 2); | |
4627 return aexpr; | |
4628 } | |
4629 | |
4630 /* Convert the bytes of an agent expression back into hex digits, so | |
4631 they can be printed or uploaded. This allocates the buffer, | |
4632 callers should free when they are done with it. */ | |
4633 | |
4634 static char * | |
4635 unparse_agent_expr (struct agent_expr *aexpr) | |
4636 { | |
4637 char *rslt; | |
4638 | |
4639 rslt = xmalloc (2 * aexpr->length + 1); | |
4640 convert_int_to_ascii (aexpr->bytes, rslt, aexpr->length); | |
4641 return rslt; | |
4642 } | |
4643 | |
4644 #endif | |
4645 | |
4646 /* A wrapper for gdb_agent_op_names that does some bounds-checking. */ | |
4647 | |
4648 static const char * | |
4649 gdb_agent_op_name (int op) | |
4650 { | |
4651 if (op < 0 || op >= gdb_agent_op_last || gdb_agent_op_names[op] == NULL) | |
4652 return "?undef?"; | |
4653 return gdb_agent_op_names[op]; | |
4654 } | |
4655 | |
4656 /* The agent expression evaluator, as specified by the GDB docs. It | |
4657 returns 0 if everything went OK, and a nonzero error code | |
4658 otherwise. */ | |
4659 | 4820 |
4660 static enum eval_result_type | 4821 static enum eval_result_type |
4661 eval_agent_expr (struct tracepoint_hit_ctx *ctx, | 4822 eval_tracepoint_agent_expr (struct tracepoint_hit_ctx *ctx, |
4662 » » struct traceframe *tframe, | 4823 » » » struct traceframe *tframe, |
4663 » » struct agent_expr *aexpr, | 4824 » » » struct agent_expr *aexpr, |
4664 » » ULONGEST *rslt) | 4825 » » » ULONGEST *rslt) |
4665 { | 4826 { |
4666 int pc = 0; | 4827 struct regcache *regcache; |
4667 #define STACK_MAX 100 | 4828 regcache = get_context_regcache (ctx); |
4668 ULONGEST stack[STACK_MAX], top; | |
4669 int sp = 0; | |
4670 unsigned char op; | |
4671 int arg; | |
4672 | 4829 |
4673 /* This union is a convenient way to convert representations. For | 4830 return gdb_eval_agent_expr (regcache, tframe, aexpr, rslt); |
4674 now, assume a standard architecture where the hardware integer | |
4675 types have 8, 16, 32, 64 bit types. A more robust solution would | |
4676 be to import stdint.h from gnulib. */ | |
4677 union | |
4678 { | |
4679 union | |
4680 { | |
4681 unsigned char bytes[1]; | |
4682 unsigned char val; | |
4683 } u8; | |
4684 union | |
4685 { | |
4686 unsigned char bytes[2]; | |
4687 unsigned short val; | |
4688 } u16; | |
4689 union | |
4690 { | |
4691 unsigned char bytes[4]; | |
4692 unsigned int val; | |
4693 } u32; | |
4694 union | |
4695 { | |
4696 unsigned char bytes[8]; | |
4697 ULONGEST val; | |
4698 } u64; | |
4699 } cnv; | |
4700 | |
4701 if (aexpr->length == 0) | |
4702 { | |
4703 trace_debug ("empty agent expression"); | |
4704 return expr_eval_empty_expression; | |
4705 } | |
4706 | |
4707 /* Cache the stack top in its own variable. Much of the time we can | |
4708 operate on this variable, rather than dinking with the stack. It | |
4709 needs to be copied to the stack when sp changes. */ | |
4710 top = 0; | |
4711 | |
4712 while (1) | |
4713 { | |
4714 op = aexpr->bytes[pc++]; | |
4715 | |
4716 trace_debug ("About to interpret byte 0x%x", op); | |
4717 | |
4718 switch (op) | |
4719 » { | |
4720 » case gdb_agent_op_add: | |
4721 » top += stack[--sp]; | |
4722 » break; | |
4723 | |
4724 » case gdb_agent_op_sub: | |
4725 » top = stack[--sp] - top; | |
4726 » break; | |
4727 | |
4728 » case gdb_agent_op_mul: | |
4729 » top *= stack[--sp]; | |
4730 » break; | |
4731 | |
4732 » case gdb_agent_op_div_signed: | |
4733 » if (top == 0) | |
4734 » { | |
4735 » trace_debug ("Attempted to divide by zero"); | |
4736 » return expr_eval_divide_by_zero; | |
4737 » } | |
4738 » top = ((LONGEST) stack[--sp]) / ((LONGEST) top); | |
4739 » break; | |
4740 | |
4741 » case gdb_agent_op_div_unsigned: | |
4742 » if (top == 0) | |
4743 » { | |
4744 » trace_debug ("Attempted to divide by zero"); | |
4745 » return expr_eval_divide_by_zero; | |
4746 » } | |
4747 » top = stack[--sp] / top; | |
4748 » break; | |
4749 | |
4750 » case gdb_agent_op_rem_signed: | |
4751 » if (top == 0) | |
4752 » { | |
4753 » trace_debug ("Attempted to divide by zero"); | |
4754 » return expr_eval_divide_by_zero; | |
4755 » } | |
4756 » top = ((LONGEST) stack[--sp]) % ((LONGEST) top); | |
4757 » break; | |
4758 | |
4759 » case gdb_agent_op_rem_unsigned: | |
4760 » if (top == 0) | |
4761 » { | |
4762 » trace_debug ("Attempted to divide by zero"); | |
4763 » return expr_eval_divide_by_zero; | |
4764 » } | |
4765 » top = stack[--sp] % top; | |
4766 » break; | |
4767 | |
4768 » case gdb_agent_op_lsh: | |
4769 » top = stack[--sp] << top; | |
4770 » break; | |
4771 | |
4772 » case gdb_agent_op_rsh_signed: | |
4773 » top = ((LONGEST) stack[--sp]) >> top; | |
4774 » break; | |
4775 | |
4776 » case gdb_agent_op_rsh_unsigned: | |
4777 » top = stack[--sp] >> top; | |
4778 » break; | |
4779 | |
4780 » case gdb_agent_op_trace: | |
4781 » agent_mem_read (tframe, | |
4782 » » » NULL, (CORE_ADDR) stack[--sp], (ULONGEST) top); | |
4783 » if (--sp >= 0) | |
4784 » top = stack[sp]; | |
4785 » break; | |
4786 | |
4787 » case gdb_agent_op_trace_quick: | |
4788 » arg = aexpr->bytes[pc++]; | |
4789 » agent_mem_read (tframe, NULL, (CORE_ADDR) top, (ULONGEST) arg); | |
4790 » break; | |
4791 | |
4792 » case gdb_agent_op_log_not: | |
4793 » top = !top; | |
4794 » break; | |
4795 | |
4796 » case gdb_agent_op_bit_and: | |
4797 » top &= stack[--sp]; | |
4798 » break; | |
4799 | |
4800 » case gdb_agent_op_bit_or: | |
4801 » top |= stack[--sp]; | |
4802 » break; | |
4803 | |
4804 » case gdb_agent_op_bit_xor: | |
4805 » top ^= stack[--sp]; | |
4806 » break; | |
4807 | |
4808 » case gdb_agent_op_bit_not: | |
4809 » top = ~top; | |
4810 » break; | |
4811 | |
4812 » case gdb_agent_op_equal: | |
4813 » top = (stack[--sp] == top); | |
4814 » break; | |
4815 | |
4816 » case gdb_agent_op_less_signed: | |
4817 » top = (((LONGEST) stack[--sp]) < ((LONGEST) top)); | |
4818 » break; | |
4819 | |
4820 » case gdb_agent_op_less_unsigned: | |
4821 » top = (stack[--sp] < top); | |
4822 » break; | |
4823 | |
4824 » case gdb_agent_op_ext: | |
4825 » arg = aexpr->bytes[pc++]; | |
4826 » if (arg < (sizeof (LONGEST) * 8)) | |
4827 » { | |
4828 » LONGEST mask = 1 << (arg - 1); | |
4829 » top &= ((LONGEST) 1 << arg) - 1; | |
4830 » top = (top ^ mask) - mask; | |
4831 » } | |
4832 » break; | |
4833 | |
4834 » case gdb_agent_op_ref8: | |
4835 » agent_mem_read (tframe, cnv.u8.bytes, (CORE_ADDR) top, 1); | |
4836 » top = cnv.u8.val; | |
4837 » break; | |
4838 | |
4839 » case gdb_agent_op_ref16: | |
4840 » agent_mem_read (tframe, cnv.u16.bytes, (CORE_ADDR) top, 2); | |
4841 » top = cnv.u16.val; | |
4842 » break; | |
4843 | |
4844 » case gdb_agent_op_ref32: | |
4845 » agent_mem_read (tframe, cnv.u32.bytes, (CORE_ADDR) top, 4); | |
4846 » top = cnv.u32.val; | |
4847 » break; | |
4848 | |
4849 » case gdb_agent_op_ref64: | |
4850 » agent_mem_read (tframe, cnv.u64.bytes, (CORE_ADDR) top, 8); | |
4851 » top = cnv.u64.val; | |
4852 » break; | |
4853 | |
4854 » case gdb_agent_op_if_goto: | |
4855 » if (top) | |
4856 » pc = (aexpr->bytes[pc] << 8) + (aexpr->bytes[pc + 1]); | |
4857 » else | |
4858 » pc += 2; | |
4859 » if (--sp >= 0) | |
4860 » top = stack[sp]; | |
4861 » break; | |
4862 | |
4863 » case gdb_agent_op_goto: | |
4864 » pc = (aexpr->bytes[pc] << 8) + (aexpr->bytes[pc + 1]); | |
4865 » break; | |
4866 | |
4867 » case gdb_agent_op_const8: | |
4868 » /* Flush the cached stack top. */ | |
4869 » stack[sp++] = top; | |
4870 » top = aexpr->bytes[pc++]; | |
4871 » break; | |
4872 | |
4873 » case gdb_agent_op_const16: | |
4874 » /* Flush the cached stack top. */ | |
4875 » stack[sp++] = top; | |
4876 » top = aexpr->bytes[pc++]; | |
4877 » top = (top << 8) + aexpr->bytes[pc++]; | |
4878 » break; | |
4879 | |
4880 » case gdb_agent_op_const32: | |
4881 » /* Flush the cached stack top. */ | |
4882 » stack[sp++] = top; | |
4883 » top = aexpr->bytes[pc++]; | |
4884 » top = (top << 8) + aexpr->bytes[pc++]; | |
4885 » top = (top << 8) + aexpr->bytes[pc++]; | |
4886 » top = (top << 8) + aexpr->bytes[pc++]; | |
4887 » break; | |
4888 | |
4889 » case gdb_agent_op_const64: | |
4890 » /* Flush the cached stack top. */ | |
4891 » stack[sp++] = top; | |
4892 » top = aexpr->bytes[pc++]; | |
4893 » top = (top << 8) + aexpr->bytes[pc++]; | |
4894 » top = (top << 8) + aexpr->bytes[pc++]; | |
4895 » top = (top << 8) + aexpr->bytes[pc++]; | |
4896 » top = (top << 8) + aexpr->bytes[pc++]; | |
4897 » top = (top << 8) + aexpr->bytes[pc++]; | |
4898 » top = (top << 8) + aexpr->bytes[pc++]; | |
4899 » top = (top << 8) + aexpr->bytes[pc++]; | |
4900 » break; | |
4901 | |
4902 » case gdb_agent_op_reg: | |
4903 » /* Flush the cached stack top. */ | |
4904 » stack[sp++] = top; | |
4905 » arg = aexpr->bytes[pc++]; | |
4906 » arg = (arg << 8) + aexpr->bytes[pc++]; | |
4907 » { | |
4908 » int regnum = arg; | |
4909 » struct regcache *regcache; | |
4910 | |
4911 » regcache = get_context_regcache (ctx); | |
4912 | |
4913 » switch (register_size (regnum)) | |
4914 » { | |
4915 » case 8: | |
4916 » » collect_register (regcache, regnum, cnv.u64.bytes); | |
4917 » » top = cnv.u64.val; | |
4918 » » break; | |
4919 » case 4: | |
4920 » » collect_register (regcache, regnum, cnv.u32.bytes); | |
4921 » » top = cnv.u32.val; | |
4922 » » break; | |
4923 » case 2: | |
4924 » » collect_register (regcache, regnum, cnv.u16.bytes); | |
4925 » » top = cnv.u16.val; | |
4926 » » break; | |
4927 » case 1: | |
4928 » » collect_register (regcache, regnum, cnv.u8.bytes); | |
4929 » » top = cnv.u8.val; | |
4930 » » break; | |
4931 » default: | |
4932 » » internal_error (__FILE__, __LINE__, | |
4933 » » » » "unhandled register size"); | |
4934 » } | |
4935 » } | |
4936 » break; | |
4937 | |
4938 » case gdb_agent_op_end: | |
4939 » trace_debug ("At end of expression, sp=%d, stack top cache=0x%s", | |
4940 » » sp, pulongest (top)); | |
4941 » if (rslt) | |
4942 » { | |
4943 » if (sp <= 0) | |
4944 » » { | |
4945 » » /* This should be an error */ | |
4946 » » trace_debug ("Stack is empty, nothing to return"); | |
4947 » » return expr_eval_empty_stack; | |
4948 » » } | |
4949 » *rslt = top; | |
4950 » } | |
4951 » return expr_eval_no_error; | |
4952 | |
4953 » case gdb_agent_op_dup: | |
4954 » stack[sp++] = top; | |
4955 » break; | |
4956 | |
4957 » case gdb_agent_op_pop: | |
4958 » if (--sp >= 0) | |
4959 » top = stack[sp]; | |
4960 » break; | |
4961 | |
4962 » case gdb_agent_op_pick: | |
4963 » arg = aexpr->bytes[pc++]; | |
4964 » stack[sp] = top; | |
4965 » top = stack[sp - arg]; | |
4966 » ++sp; | |
4967 » break; | |
4968 | |
4969 » case gdb_agent_op_rot: | |
4970 » { | |
4971 » ULONGEST tem = stack[sp - 1]; | |
4972 | |
4973 » stack[sp - 1] = stack[sp - 2]; | |
4974 » stack[sp - 2] = top; | |
4975 » top = tem; | |
4976 » } | |
4977 » break; | |
4978 | |
4979 » case gdb_agent_op_zero_ext: | |
4980 » arg = aexpr->bytes[pc++]; | |
4981 » if (arg < (sizeof (LONGEST) * 8)) | |
4982 » top &= ((LONGEST) 1 << arg) - 1; | |
4983 » break; | |
4984 | |
4985 » case gdb_agent_op_swap: | |
4986 » /* Interchange top two stack elements, making sure top gets | |
4987 » copied back onto stack. */ | |
4988 » stack[sp] = top; | |
4989 » top = stack[sp - 1]; | |
4990 » stack[sp - 1] = stack[sp]; | |
4991 » break; | |
4992 | |
4993 » case gdb_agent_op_getv: | |
4994 » /* Flush the cached stack top. */ | |
4995 » stack[sp++] = top; | |
4996 » arg = aexpr->bytes[pc++]; | |
4997 » arg = (arg << 8) + aexpr->bytes[pc++]; | |
4998 » top = get_trace_state_variable_value (arg); | |
4999 » break; | |
5000 | |
5001 » case gdb_agent_op_setv: | |
5002 » arg = aexpr->bytes[pc++]; | |
5003 » arg = (arg << 8) + aexpr->bytes[pc++]; | |
5004 » set_trace_state_variable_value (arg, top); | |
5005 » /* Note that we leave the value on the stack, for the | |
5006 » benefit of later/enclosing expressions. */ | |
5007 » break; | |
5008 | |
5009 » case gdb_agent_op_tracev: | |
5010 » arg = aexpr->bytes[pc++]; | |
5011 » arg = (arg << 8) + aexpr->bytes[pc++]; | |
5012 » agent_tsv_read (tframe, arg); | |
5013 » break; | |
5014 | |
5015 » case gdb_agent_op_tracenz: | |
5016 » agent_mem_read_string (tframe, NULL, (CORE_ADDR) stack[--sp], | |
5017 » » » » (ULONGEST) top); | |
5018 » if (--sp >= 0) | |
5019 » top = stack[sp]; | |
5020 » break; | |
5021 | |
5022 » /* GDB never (currently) generates any of these ops. */ | |
5023 » case gdb_agent_op_float: | |
5024 » case gdb_agent_op_ref_float: | |
5025 » case gdb_agent_op_ref_double: | |
5026 » case gdb_agent_op_ref_long_double: | |
5027 » case gdb_agent_op_l_to_d: | |
5028 » case gdb_agent_op_d_to_l: | |
5029 » case gdb_agent_op_trace16: | |
5030 » trace_debug ("Agent expression op 0x%x valid, but not handled", | |
5031 » » op); | |
5032 » /* If ever GDB generates any of these, we don't have the | |
5033 » option of ignoring. */ | |
5034 » return 1; | |
5035 | |
5036 » default: | |
5037 » trace_debug ("Agent expression op 0x%x not recognized", op); | |
5038 » /* Don't struggle on, things will just get worse. */ | |
5039 » return expr_eval_unrecognized_opcode; | |
5040 » } | |
5041 | |
5042 /* Check for stack badness. */ | |
5043 if (sp >= (STACK_MAX - 1)) | |
5044 » { | |
5045 » trace_debug ("Expression stack overflow"); | |
5046 » return expr_eval_stack_overflow; | |
5047 » } | |
5048 | |
5049 if (sp < 0) | |
5050 » { | |
5051 » trace_debug ("Expression stack underflow"); | |
5052 » return expr_eval_stack_underflow; | |
5053 » } | |
5054 | |
5055 trace_debug ("Op %s -> sp=%d, top=0x%s", | |
5056 » » gdb_agent_op_name (op), sp, pulongest (top)); | |
5057 } | |
5058 } | 4831 } |
5059 | 4832 |
5060 /* Do memory copies for bytecodes. */ | 4833 /* Do memory copies for bytecodes. */ |
5061 /* Do the recording of memory blocks for actions and bytecodes. */ | 4834 /* Do the recording of memory blocks for actions and bytecodes. */ |
5062 | 4835 |
5063 static int | 4836 int |
5064 agent_mem_read (struct traceframe *tframe, | 4837 agent_mem_read (struct traceframe *tframe, |
5065 unsigned char *to, CORE_ADDR from, ULONGEST len) | 4838 unsigned char *to, CORE_ADDR from, ULONGEST len) |
5066 { | 4839 { |
5067 unsigned char *mspace; | 4840 unsigned char *mspace; |
5068 ULONGEST remaining = len; | 4841 ULONGEST remaining = len; |
5069 unsigned short blocklen; | 4842 unsigned short blocklen; |
5070 | 4843 |
5071 /* If a 'to' buffer is specified, use it. */ | 4844 /* If a 'to' buffer is specified, use it. */ |
5072 if (to != NULL) | 4845 if (to != NULL) |
5073 { | 4846 { |
(...skipping 21 matching lines...) Expand all Loading... |
5095 mspace += sizeof (blocklen); | 4868 mspace += sizeof (blocklen); |
5096 /* Record the memory block proper. */ | 4869 /* Record the memory block proper. */ |
5097 read_inferior_memory (from, mspace, blocklen); | 4870 read_inferior_memory (from, mspace, blocklen); |
5098 trace_debug ("%d bytes recorded", blocklen); | 4871 trace_debug ("%d bytes recorded", blocklen); |
5099 remaining -= blocklen; | 4872 remaining -= blocklen; |
5100 from += blocklen; | 4873 from += blocklen; |
5101 } | 4874 } |
5102 return 0; | 4875 return 0; |
5103 } | 4876 } |
5104 | 4877 |
5105 static int | 4878 int |
5106 agent_mem_read_string (struct traceframe *tframe, | 4879 agent_mem_read_string (struct traceframe *tframe, |
5107 unsigned char *to, CORE_ADDR from, ULONGEST len) | 4880 unsigned char *to, CORE_ADDR from, ULONGEST len) |
5108 { | 4881 { |
5109 unsigned char *buf, *mspace; | 4882 unsigned char *buf, *mspace; |
5110 ULONGEST remaining = len; | 4883 ULONGEST remaining = len; |
5111 unsigned short blocklen, i; | 4884 unsigned short blocklen, i; |
5112 | 4885 |
5113 /* To save a bit of space, block lengths are 16-bit, so break large | 4886 /* To save a bit of space, block lengths are 16-bit, so break large |
5114 requests into multiple blocks. Bordering on overkill for strings, | 4887 requests into multiple blocks. Bordering on overkill for strings, |
5115 but it could happen that someone specifies a large max length. */ | 4888 but it could happen that someone specifies a large max length. */ |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5157 memcpy ((void *) mspace, (void *) buf, blocklen); | 4930 memcpy ((void *) mspace, (void *) buf, blocklen); |
5158 remaining -= blocklen; | 4931 remaining -= blocklen; |
5159 from += blocklen; | 4932 from += blocklen; |
5160 xfree (buf); | 4933 xfree (buf); |
5161 } | 4934 } |
5162 return 0; | 4935 return 0; |
5163 } | 4936 } |
5164 | 4937 |
5165 /* Record the value of a trace state variable. */ | 4938 /* Record the value of a trace state variable. */ |
5166 | 4939 |
5167 static int | 4940 int |
5168 agent_tsv_read (struct traceframe *tframe, int n) | 4941 agent_tsv_read (struct traceframe *tframe, int n) |
5169 { | 4942 { |
5170 unsigned char *vspace; | 4943 unsigned char *vspace; |
5171 LONGEST val; | 4944 LONGEST val; |
5172 | 4945 |
5173 vspace = add_traceframe_block (tframe, | 4946 vspace = add_traceframe_block (tframe, |
5174 1 + sizeof (n) + sizeof (LONGEST)); | 4947 1 + sizeof (n) + sizeof (LONGEST)); |
5175 if (vspace == NULL) | 4948 if (vspace == NULL) |
5176 return 1; | 4949 return 1; |
5177 /* Identify block as a variable. */ | 4950 /* Identify block as a variable. */ |
(...skipping 772 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5950 break; | 5723 break; |
5951 } | 5724 } |
5952 } | 5725 } |
5953 } | 5726 } |
5954 } | 5727 } |
5955 | 5728 |
5956 #endif | 5729 #endif |
5957 | 5730 |
5958 #ifndef IN_PROCESS_AGENT | 5731 #ifndef IN_PROCESS_AGENT |
5959 | 5732 |
5960 /* Bytecode compilation. */ | |
5961 | |
5962 CORE_ADDR current_insn_ptr; | |
5963 | |
5964 int emit_error; | |
5965 | |
5966 struct bytecode_address | |
5967 { | |
5968 int pc; | |
5969 CORE_ADDR address; | |
5970 int goto_pc; | |
5971 /* Offset and size of field to be modified in the goto block. */ | |
5972 int from_offset, from_size; | |
5973 struct bytecode_address *next; | |
5974 } *bytecode_address_table; | |
5975 | |
5976 CORE_ADDR | 5733 CORE_ADDR |
5977 get_raw_reg_func_addr (void) | 5734 get_raw_reg_func_addr (void) |
5978 { | 5735 { |
5979 return ipa_sym_addrs.addr_get_raw_reg; | 5736 return ipa_sym_addrs.addr_get_raw_reg; |
5980 } | 5737 } |
5981 | 5738 |
5982 static void | 5739 CORE_ADDR |
5983 emit_prologue (void) | 5740 get_get_tsv_func_addr (void) |
5984 { | 5741 { |
5985 target_emit_ops ()->emit_prologue (); | 5742 return ipa_sym_addrs.addr_get_trace_state_variable_value; |
5986 } | 5743 } |
5987 | 5744 |
5988 static void | 5745 CORE_ADDR |
5989 emit_epilogue (void) | 5746 get_set_tsv_func_addr (void) |
5990 { | 5747 { |
5991 target_emit_ops ()->emit_epilogue (); | 5748 return ipa_sym_addrs.addr_set_trace_state_variable_value; |
5992 } | 5749 } |
5993 | 5750 |
5994 static void | 5751 static void |
5995 emit_add (void) | |
5996 { | |
5997 target_emit_ops ()->emit_add (); | |
5998 } | |
5999 | |
6000 static void | |
6001 emit_sub (void) | |
6002 { | |
6003 target_emit_ops ()->emit_sub (); | |
6004 } | |
6005 | |
6006 static void | |
6007 emit_mul (void) | |
6008 { | |
6009 target_emit_ops ()->emit_mul (); | |
6010 } | |
6011 | |
6012 static void | |
6013 emit_lsh (void) | |
6014 { | |
6015 target_emit_ops ()->emit_lsh (); | |
6016 } | |
6017 | |
6018 static void | |
6019 emit_rsh_signed (void) | |
6020 { | |
6021 target_emit_ops ()->emit_rsh_signed (); | |
6022 } | |
6023 | |
6024 static void | |
6025 emit_rsh_unsigned (void) | |
6026 { | |
6027 target_emit_ops ()->emit_rsh_unsigned (); | |
6028 } | |
6029 | |
6030 static void | |
6031 emit_ext (int arg) | |
6032 { | |
6033 target_emit_ops ()->emit_ext (arg); | |
6034 } | |
6035 | |
6036 static void | |
6037 emit_log_not (void) | |
6038 { | |
6039 target_emit_ops ()->emit_log_not (); | |
6040 } | |
6041 | |
6042 static void | |
6043 emit_bit_and (void) | |
6044 { | |
6045 target_emit_ops ()->emit_bit_and (); | |
6046 } | |
6047 | |
6048 static void | |
6049 emit_bit_or (void) | |
6050 { | |
6051 target_emit_ops ()->emit_bit_or (); | |
6052 } | |
6053 | |
6054 static void | |
6055 emit_bit_xor (void) | |
6056 { | |
6057 target_emit_ops ()->emit_bit_xor (); | |
6058 } | |
6059 | |
6060 static void | |
6061 emit_bit_not (void) | |
6062 { | |
6063 target_emit_ops ()->emit_bit_not (); | |
6064 } | |
6065 | |
6066 static void | |
6067 emit_equal (void) | |
6068 { | |
6069 target_emit_ops ()->emit_equal (); | |
6070 } | |
6071 | |
6072 static void | |
6073 emit_less_signed (void) | |
6074 { | |
6075 target_emit_ops ()->emit_less_signed (); | |
6076 } | |
6077 | |
6078 static void | |
6079 emit_less_unsigned (void) | |
6080 { | |
6081 target_emit_ops ()->emit_less_unsigned (); | |
6082 } | |
6083 | |
6084 static void | |
6085 emit_ref (int size) | |
6086 { | |
6087 target_emit_ops ()->emit_ref (size); | |
6088 } | |
6089 | |
6090 static void | |
6091 emit_if_goto (int *offset_p, int *size_p) | |
6092 { | |
6093 target_emit_ops ()->emit_if_goto (offset_p, size_p); | |
6094 } | |
6095 | |
6096 static void | |
6097 emit_goto (int *offset_p, int *size_p) | |
6098 { | |
6099 target_emit_ops ()->emit_goto (offset_p, size_p); | |
6100 } | |
6101 | |
6102 static void | |
6103 write_goto_address (CORE_ADDR from, CORE_ADDR to, int size) | |
6104 { | |
6105 target_emit_ops ()->write_goto_address (from, to, size); | |
6106 } | |
6107 | |
6108 static void | |
6109 emit_const (LONGEST num) | |
6110 { | |
6111 target_emit_ops ()->emit_const (num); | |
6112 } | |
6113 | |
6114 static void | |
6115 emit_reg (int reg) | |
6116 { | |
6117 target_emit_ops ()->emit_reg (reg); | |
6118 } | |
6119 | |
6120 static void | |
6121 emit_pop (void) | |
6122 { | |
6123 target_emit_ops ()->emit_pop (); | |
6124 } | |
6125 | |
6126 static void | |
6127 emit_stack_flush (void) | |
6128 { | |
6129 target_emit_ops ()->emit_stack_flush (); | |
6130 } | |
6131 | |
6132 static void | |
6133 emit_zero_ext (int arg) | |
6134 { | |
6135 target_emit_ops ()->emit_zero_ext (arg); | |
6136 } | |
6137 | |
6138 static void | |
6139 emit_swap (void) | |
6140 { | |
6141 target_emit_ops ()->emit_swap (); | |
6142 } | |
6143 | |
6144 static void | |
6145 emit_stack_adjust (int n) | |
6146 { | |
6147 target_emit_ops ()->emit_stack_adjust (n); | |
6148 } | |
6149 | |
6150 /* FN's prototype is `LONGEST(*fn)(int)'. */ | |
6151 | |
6152 static void | |
6153 emit_int_call_1 (CORE_ADDR fn, int arg1) | |
6154 { | |
6155 target_emit_ops ()->emit_int_call_1 (fn, arg1); | |
6156 } | |
6157 | |
6158 /* FN's prototype is `void(*fn)(int,LONGEST)'. */ | |
6159 | |
6160 static void | |
6161 emit_void_call_2 (CORE_ADDR fn, int arg1) | |
6162 { | |
6163 target_emit_ops ()->emit_void_call_2 (fn, arg1); | |
6164 } | |
6165 | |
6166 static void | |
6167 emit_eq_goto (int *offset_p, int *size_p) | |
6168 { | |
6169 target_emit_ops ()->emit_eq_goto (offset_p, size_p); | |
6170 } | |
6171 | |
6172 static void | |
6173 emit_ne_goto (int *offset_p, int *size_p) | |
6174 { | |
6175 target_emit_ops ()->emit_ne_goto (offset_p, size_p); | |
6176 } | |
6177 | |
6178 static void | |
6179 emit_lt_goto (int *offset_p, int *size_p) | |
6180 { | |
6181 target_emit_ops ()->emit_lt_goto (offset_p, size_p); | |
6182 } | |
6183 | |
6184 static void | |
6185 emit_ge_goto (int *offset_p, int *size_p) | |
6186 { | |
6187 target_emit_ops ()->emit_ge_goto (offset_p, size_p); | |
6188 } | |
6189 | |
6190 static void | |
6191 emit_gt_goto (int *offset_p, int *size_p) | |
6192 { | |
6193 target_emit_ops ()->emit_gt_goto (offset_p, size_p); | |
6194 } | |
6195 | |
6196 static void | |
6197 emit_le_goto (int *offset_p, int *size_p) | |
6198 { | |
6199 target_emit_ops ()->emit_le_goto (offset_p, size_p); | |
6200 } | |
6201 | |
6202 static enum eval_result_type compile_bytecodes (struct agent_expr *aexpr); | |
6203 | |
6204 static void | |
6205 compile_tracepoint_condition (struct tracepoint *tpoint, | 5752 compile_tracepoint_condition (struct tracepoint *tpoint, |
6206 CORE_ADDR *jump_entry) | 5753 CORE_ADDR *jump_entry) |
6207 { | 5754 { |
6208 CORE_ADDR entry_point = *jump_entry; | 5755 CORE_ADDR entry_point = *jump_entry; |
6209 enum eval_result_type err; | 5756 enum eval_result_type err; |
6210 | 5757 |
6211 trace_debug ("Starting condition compilation for tracepoint %d\n", | 5758 trace_debug ("Starting condition compilation for tracepoint %d\n", |
6212 tpoint->number); | 5759 tpoint->number); |
6213 | 5760 |
6214 /* Initialize the global pointer to the code being built. */ | 5761 /* Initialize the global pointer to the code being built. */ |
(...skipping 26 matching lines...) Expand all Loading... |
6241 | 5788 |
6242 /* Update the code pointer passed in. Note that we do this even if | 5789 /* Update the code pointer passed in. Note that we do this even if |
6243 the compile fails, so that we can look at the partial results | 5790 the compile fails, so that we can look at the partial results |
6244 instead of letting them be overwritten. */ | 5791 instead of letting them be overwritten. */ |
6245 *jump_entry = current_insn_ptr; | 5792 *jump_entry = current_insn_ptr; |
6246 | 5793 |
6247 /* Leave a gap, to aid dump decipherment. */ | 5794 /* Leave a gap, to aid dump decipherment. */ |
6248 *jump_entry += 16; | 5795 *jump_entry += 16; |
6249 } | 5796 } |
6250 | 5797 |
6251 /* Scan an agent expression for any evidence that the given PC is the | |
6252 target of a jump bytecode in the expression. */ | |
6253 | |
6254 int | |
6255 is_goto_target (struct agent_expr *aexpr, int pc) | |
6256 { | |
6257 int i; | |
6258 unsigned char op; | |
6259 | |
6260 for (i = 0; i < aexpr->length; i += 1 + gdb_agent_op_sizes[op]) | |
6261 { | |
6262 op = aexpr->bytes[i]; | |
6263 | |
6264 if (op == gdb_agent_op_goto || op == gdb_agent_op_if_goto) | |
6265 { | |
6266 int target = (aexpr->bytes[i + 1] << 8) + aexpr->bytes[i + 2]; | |
6267 if (target == pc) | |
6268 return 1; | |
6269 } | |
6270 } | |
6271 | |
6272 return 0; | |
6273 } | |
6274 | |
6275 /* Given an agent expression, turn it into native code. */ | |
6276 | |
6277 static enum eval_result_type | |
6278 compile_bytecodes (struct agent_expr *aexpr) | |
6279 { | |
6280 int pc = 0; | |
6281 int done = 0; | |
6282 unsigned char op, next_op; | |
6283 int arg; | |
6284 /* This is only used to build 64-bit value for constants. */ | |
6285 ULONGEST top; | |
6286 struct bytecode_address *aentry, *aentry2; | |
6287 | |
6288 #define UNHANDLED \ | |
6289 do \ | |
6290 { \ | |
6291 trace_debug ("Cannot compile op 0x%x\n", op); \ | |
6292 return expr_eval_unhandled_opcode; \ | |
6293 } while (0) | |
6294 | |
6295 if (aexpr->length == 0) | |
6296 { | |
6297 trace_debug ("empty agent expression\n"); | |
6298 return expr_eval_empty_expression; | |
6299 } | |
6300 | |
6301 bytecode_address_table = NULL; | |
6302 | |
6303 while (!done) | |
6304 { | |
6305 op = aexpr->bytes[pc]; | |
6306 | |
6307 trace_debug ("About to compile op 0x%x, pc=%d\n", op, pc); | |
6308 | |
6309 /* Record the compiled-code address of the bytecode, for use by | |
6310 jump instructions. */ | |
6311 aentry = xmalloc (sizeof (struct bytecode_address)); | |
6312 aentry->pc = pc; | |
6313 aentry->address = current_insn_ptr; | |
6314 aentry->goto_pc = -1; | |
6315 aentry->from_offset = aentry->from_size = 0; | |
6316 aentry->next = bytecode_address_table; | |
6317 bytecode_address_table = aentry; | |
6318 | |
6319 ++pc; | |
6320 | |
6321 emit_error = 0; | |
6322 | |
6323 switch (op) | |
6324 { | |
6325 case gdb_agent_op_add: | |
6326 emit_add (); | |
6327 break; | |
6328 | |
6329 case gdb_agent_op_sub: | |
6330 emit_sub (); | |
6331 break; | |
6332 | |
6333 case gdb_agent_op_mul: | |
6334 emit_mul (); | |
6335 break; | |
6336 | |
6337 case gdb_agent_op_div_signed: | |
6338 UNHANDLED; | |
6339 break; | |
6340 | |
6341 case gdb_agent_op_div_unsigned: | |
6342 UNHANDLED; | |
6343 break; | |
6344 | |
6345 case gdb_agent_op_rem_signed: | |
6346 UNHANDLED; | |
6347 break; | |
6348 | |
6349 case gdb_agent_op_rem_unsigned: | |
6350 UNHANDLED; | |
6351 break; | |
6352 | |
6353 case gdb_agent_op_lsh: | |
6354 emit_lsh (); | |
6355 break; | |
6356 | |
6357 case gdb_agent_op_rsh_signed: | |
6358 emit_rsh_signed (); | |
6359 break; | |
6360 | |
6361 case gdb_agent_op_rsh_unsigned: | |
6362 emit_rsh_unsigned (); | |
6363 break; | |
6364 | |
6365 case gdb_agent_op_trace: | |
6366 UNHANDLED; | |
6367 break; | |
6368 | |
6369 case gdb_agent_op_trace_quick: | |
6370 UNHANDLED; | |
6371 break; | |
6372 | |
6373 case gdb_agent_op_log_not: | |
6374 emit_log_not (); | |
6375 break; | |
6376 | |
6377 case gdb_agent_op_bit_and: | |
6378 emit_bit_and (); | |
6379 break; | |
6380 | |
6381 case gdb_agent_op_bit_or: | |
6382 emit_bit_or (); | |
6383 break; | |
6384 | |
6385 case gdb_agent_op_bit_xor: | |
6386 emit_bit_xor (); | |
6387 break; | |
6388 | |
6389 case gdb_agent_op_bit_not: | |
6390 emit_bit_not (); | |
6391 break; | |
6392 | |
6393 case gdb_agent_op_equal: | |
6394 next_op = aexpr->bytes[pc]; | |
6395 if (next_op == gdb_agent_op_if_goto | |
6396 && !is_goto_target (aexpr, pc) | |
6397 && target_emit_ops ()->emit_eq_goto) | |
6398 { | |
6399 trace_debug ("Combining equal & if_goto"); | |
6400 pc += 1; | |
6401 aentry->pc = pc; | |
6402 arg = aexpr->bytes[pc++]; | |
6403 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6404 aentry->goto_pc = arg; | |
6405 emit_eq_goto (&(aentry->from_offset), &(aentry->from_size)); | |
6406 } | |
6407 else if (next_op == gdb_agent_op_log_not | |
6408 && (aexpr->bytes[pc + 1] == gdb_agent_op_if_goto) | |
6409 && !is_goto_target (aexpr, pc + 1) | |
6410 && target_emit_ops ()->emit_ne_goto) | |
6411 { | |
6412 trace_debug ("Combining equal & log_not & if_goto"); | |
6413 pc += 2; | |
6414 aentry->pc = pc; | |
6415 arg = aexpr->bytes[pc++]; | |
6416 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6417 aentry->goto_pc = arg; | |
6418 emit_ne_goto (&(aentry->from_offset), &(aentry->from_size)); | |
6419 } | |
6420 else | |
6421 emit_equal (); | |
6422 break; | |
6423 | |
6424 case gdb_agent_op_less_signed: | |
6425 next_op = aexpr->bytes[pc]; | |
6426 if (next_op == gdb_agent_op_if_goto | |
6427 && !is_goto_target (aexpr, pc)) | |
6428 { | |
6429 trace_debug ("Combining less_signed & if_goto"); | |
6430 pc += 1; | |
6431 aentry->pc = pc; | |
6432 arg = aexpr->bytes[pc++]; | |
6433 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6434 aentry->goto_pc = arg; | |
6435 emit_lt_goto (&(aentry->from_offset), &(aentry->from_size)); | |
6436 } | |
6437 else if (next_op == gdb_agent_op_log_not | |
6438 && !is_goto_target (aexpr, pc) | |
6439 && (aexpr->bytes[pc + 1] == gdb_agent_op_if_goto) | |
6440 && !is_goto_target (aexpr, pc + 1)) | |
6441 { | |
6442 trace_debug ("Combining less_signed & log_not & if_goto"); | |
6443 pc += 2; | |
6444 aentry->pc = pc; | |
6445 arg = aexpr->bytes[pc++]; | |
6446 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6447 aentry->goto_pc = arg; | |
6448 emit_ge_goto (&(aentry->from_offset), &(aentry->from_size)); | |
6449 } | |
6450 else | |
6451 emit_less_signed (); | |
6452 break; | |
6453 | |
6454 case gdb_agent_op_less_unsigned: | |
6455 emit_less_unsigned (); | |
6456 break; | |
6457 | |
6458 case gdb_agent_op_ext: | |
6459 arg = aexpr->bytes[pc++]; | |
6460 if (arg < (sizeof (LONGEST) * 8)) | |
6461 emit_ext (arg); | |
6462 break; | |
6463 | |
6464 case gdb_agent_op_ref8: | |
6465 emit_ref (1); | |
6466 break; | |
6467 | |
6468 case gdb_agent_op_ref16: | |
6469 emit_ref (2); | |
6470 break; | |
6471 | |
6472 case gdb_agent_op_ref32: | |
6473 emit_ref (4); | |
6474 break; | |
6475 | |
6476 case gdb_agent_op_ref64: | |
6477 emit_ref (8); | |
6478 break; | |
6479 | |
6480 case gdb_agent_op_if_goto: | |
6481 arg = aexpr->bytes[pc++]; | |
6482 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6483 aentry->goto_pc = arg; | |
6484 emit_if_goto (&(aentry->from_offset), &(aentry->from_size)); | |
6485 break; | |
6486 | |
6487 case gdb_agent_op_goto: | |
6488 arg = aexpr->bytes[pc++]; | |
6489 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6490 aentry->goto_pc = arg; | |
6491 emit_goto (&(aentry->from_offset), &(aentry->from_size)); | |
6492 break; | |
6493 | |
6494 case gdb_agent_op_const8: | |
6495 emit_stack_flush (); | |
6496 top = aexpr->bytes[pc++]; | |
6497 emit_const (top); | |
6498 break; | |
6499 | |
6500 case gdb_agent_op_const16: | |
6501 emit_stack_flush (); | |
6502 top = aexpr->bytes[pc++]; | |
6503 top = (top << 8) + aexpr->bytes[pc++]; | |
6504 emit_const (top); | |
6505 break; | |
6506 | |
6507 case gdb_agent_op_const32: | |
6508 emit_stack_flush (); | |
6509 top = aexpr->bytes[pc++]; | |
6510 top = (top << 8) + aexpr->bytes[pc++]; | |
6511 top = (top << 8) + aexpr->bytes[pc++]; | |
6512 top = (top << 8) + aexpr->bytes[pc++]; | |
6513 emit_const (top); | |
6514 break; | |
6515 | |
6516 case gdb_agent_op_const64: | |
6517 emit_stack_flush (); | |
6518 top = aexpr->bytes[pc++]; | |
6519 top = (top << 8) + aexpr->bytes[pc++]; | |
6520 top = (top << 8) + aexpr->bytes[pc++]; | |
6521 top = (top << 8) + aexpr->bytes[pc++]; | |
6522 top = (top << 8) + aexpr->bytes[pc++]; | |
6523 top = (top << 8) + aexpr->bytes[pc++]; | |
6524 top = (top << 8) + aexpr->bytes[pc++]; | |
6525 top = (top << 8) + aexpr->bytes[pc++]; | |
6526 emit_const (top); | |
6527 break; | |
6528 | |
6529 case gdb_agent_op_reg: | |
6530 emit_stack_flush (); | |
6531 arg = aexpr->bytes[pc++]; | |
6532 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6533 emit_reg (arg); | |
6534 break; | |
6535 | |
6536 case gdb_agent_op_end: | |
6537 trace_debug ("At end of expression\n"); | |
6538 | |
6539 /* Assume there is one stack element left, and that it is | |
6540 cached in "top" where emit_epilogue can get to it. */ | |
6541 emit_stack_adjust (1); | |
6542 | |
6543 done = 1; | |
6544 break; | |
6545 | |
6546 case gdb_agent_op_dup: | |
6547 /* In our design, dup is equivalent to stack flushing. */ | |
6548 emit_stack_flush (); | |
6549 break; | |
6550 | |
6551 case gdb_agent_op_pop: | |
6552 emit_pop (); | |
6553 break; | |
6554 | |
6555 case gdb_agent_op_zero_ext: | |
6556 arg = aexpr->bytes[pc++]; | |
6557 if (arg < (sizeof (LONGEST) * 8)) | |
6558 emit_zero_ext (arg); | |
6559 break; | |
6560 | |
6561 case gdb_agent_op_swap: | |
6562 next_op = aexpr->bytes[pc]; | |
6563 /* Detect greater-than comparison sequences. */ | |
6564 if (next_op == gdb_agent_op_less_signed | |
6565 && !is_goto_target (aexpr, pc) | |
6566 && (aexpr->bytes[pc + 1] == gdb_agent_op_if_goto) | |
6567 && !is_goto_target (aexpr, pc + 1)) | |
6568 { | |
6569 trace_debug ("Combining swap & less_signed & if_goto"); | |
6570 pc += 2; | |
6571 aentry->pc = pc; | |
6572 arg = aexpr->bytes[pc++]; | |
6573 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6574 aentry->goto_pc = arg; | |
6575 emit_gt_goto (&(aentry->from_offset), &(aentry->from_size)); | |
6576 } | |
6577 else if (next_op == gdb_agent_op_less_signed | |
6578 && !is_goto_target (aexpr, pc) | |
6579 && (aexpr->bytes[pc + 1] == gdb_agent_op_log_not) | |
6580 && !is_goto_target (aexpr, pc + 1) | |
6581 && (aexpr->bytes[pc + 2] == gdb_agent_op_if_goto) | |
6582 && !is_goto_target (aexpr, pc + 2)) | |
6583 { | |
6584 trace_debug ("Combining swap & less_signed & log_not & if_goto"); | |
6585 pc += 3; | |
6586 aentry->pc = pc; | |
6587 arg = aexpr->bytes[pc++]; | |
6588 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6589 aentry->goto_pc = arg; | |
6590 emit_le_goto (&(aentry->from_offset), &(aentry->from_size)); | |
6591 } | |
6592 else | |
6593 emit_swap (); | |
6594 break; | |
6595 | |
6596 case gdb_agent_op_getv: | |
6597 emit_stack_flush (); | |
6598 arg = aexpr->bytes[pc++]; | |
6599 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6600 emit_int_call_1 (ipa_sym_addrs.addr_get_trace_state_variable_value, | |
6601 arg); | |
6602 break; | |
6603 | |
6604 case gdb_agent_op_setv: | |
6605 arg = aexpr->bytes[pc++]; | |
6606 arg = (arg << 8) + aexpr->bytes[pc++]; | |
6607 emit_void_call_2 (ipa_sym_addrs.addr_set_trace_state_variable_value, | |
6608 arg); | |
6609 break; | |
6610 | |
6611 case gdb_agent_op_tracev: | |
6612 UNHANDLED; | |
6613 break; | |
6614 | |
6615 /* GDB never (currently) generates any of these ops. */ | |
6616 case gdb_agent_op_float: | |
6617 case gdb_agent_op_ref_float: | |
6618 case gdb_agent_op_ref_double: | |
6619 case gdb_agent_op_ref_long_double: | |
6620 case gdb_agent_op_l_to_d: | |
6621 case gdb_agent_op_d_to_l: | |
6622 case gdb_agent_op_trace16: | |
6623 UNHANDLED; | |
6624 break; | |
6625 | |
6626 default: | |
6627 trace_debug ("Agent expression op 0x%x not recognized\n", op); | |
6628 /* Don't struggle on, things will just get worse. */ | |
6629 return expr_eval_unrecognized_opcode; | |
6630 } | |
6631 | |
6632 /* This catches errors that occur in target-specific code | |
6633 emission. */ | |
6634 if (emit_error) | |
6635 { | |
6636 trace_debug ("Error %d while emitting code for %s\n", | |
6637 emit_error, gdb_agent_op_name (op)); | |
6638 return expr_eval_unhandled_opcode; | |
6639 } | |
6640 | |
6641 trace_debug ("Op %s compiled\n", gdb_agent_op_name (op)); | |
6642 } | |
6643 | |
6644 /* Now fill in real addresses as goto destinations. */ | |
6645 for (aentry = bytecode_address_table; aentry; aentry = aentry->next) | |
6646 { | |
6647 int written = 0; | |
6648 | |
6649 if (aentry->goto_pc < 0) | |
6650 continue; | |
6651 | |
6652 /* Find the location that we are going to, and call back into | |
6653 target-specific code to write the actual address or | |
6654 displacement. */ | |
6655 for (aentry2 = bytecode_address_table; aentry2; aentry2 = aentry2->next) | |
6656 { | |
6657 if (aentry2->pc == aentry->goto_pc) | |
6658 { | |
6659 trace_debug ("Want to jump from %s to %s\n", | |
6660 paddress (aentry->address), | |
6661 paddress (aentry2->address)); | |
6662 write_goto_address (aentry->address + aentry->from_offset, | |
6663 aentry2->address, aentry->from_size); | |
6664 written = 1; | |
6665 break; | |
6666 } | |
6667 } | |
6668 | |
6669 /* Error out if we didn't find a destination. */ | |
6670 if (!written) | |
6671 { | |
6672 trace_debug ("Destination of goto %d not found\n", | |
6673 aentry->goto_pc); | |
6674 return expr_eval_invalid_goto; | |
6675 } | |
6676 } | |
6677 | |
6678 return expr_eval_no_error; | |
6679 } | |
6680 | |
6681 /* We'll need to adjust these when we consider bi-arch setups, and big | 5798 /* We'll need to adjust these when we consider bi-arch setups, and big |
6682 endian machines. */ | 5799 endian machines. */ |
6683 | 5800 |
6684 static int | 5801 static int |
6685 write_inferior_data_ptr (CORE_ADDR where, CORE_ADDR ptr) | 5802 write_inferior_data_ptr (CORE_ADDR where, CORE_ADDR ptr) |
6686 { | 5803 { |
6687 return write_inferior_memory (where, | 5804 return write_inferior_memory (where, |
6688 (unsigned char *) &ptr, sizeof (void *)); | 5805 (unsigned char *) &ptr, sizeof (void *)); |
6689 } | 5806 } |
6690 | 5807 |
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6801 /* The pointers array. */ | 5918 /* The pointers array. */ |
6802 actions_array | 5919 actions_array |
6803 = target_malloc (sizeof (*tpoint->actions) * tpoint->numactions); | 5920 = target_malloc (sizeof (*tpoint->actions) * tpoint->numactions); |
6804 write_inferior_data_ptr (tpptr + offsetof (struct tracepoint, | 5921 write_inferior_data_ptr (tpptr + offsetof (struct tracepoint, |
6805 actions), | 5922 actions), |
6806 actions_array); | 5923 actions_array); |
6807 | 5924 |
6808 /* Now for each pointer, download the action. */ | 5925 /* Now for each pointer, download the action. */ |
6809 for (i = 0; i < tpoint->numactions; i++) | 5926 for (i = 0; i < tpoint->numactions; i++) |
6810 { | 5927 { |
6811 CORE_ADDR ipa_action = 0; | |
6812 struct tracepoint_action *action = tpoint->actions[i]; | 5928 struct tracepoint_action *action = tpoint->actions[i]; |
6813 | 5929 » CORE_ADDR ipa_action = action->ops->download (action); |
6814 » switch (action->type) | |
6815 » { | |
6816 » case 'M': | |
6817 » ipa_action | |
6818 » » = target_malloc (sizeof (struct collect_memory_action)); | |
6819 » write_inferior_memory (ipa_action, | |
6820 » » » » (unsigned char *) action, | |
6821 » » » » sizeof (struct collect_memory_action)); | |
6822 » break; | |
6823 » case 'R': | |
6824 » ipa_action | |
6825 » » = target_malloc (sizeof (struct collect_registers_action)); | |
6826 » write_inferior_memory (ipa_action, | |
6827 » » » » (unsigned char *) action, | |
6828 » » » » sizeof (struct collect_registers_action)); | |
6829 » break; | |
6830 » case 'X': | |
6831 » { | |
6832 » » CORE_ADDR expr; | |
6833 » » struct eval_expr_action *eaction | |
6834 » » = (struct eval_expr_action *) action; | |
6835 | |
6836 » » ipa_action = target_malloc (sizeof (*eaction)); | |
6837 » » write_inferior_memory (ipa_action, | |
6838 » » » » (unsigned char *) eaction, | |
6839 » » » » sizeof (*eaction)); | |
6840 | |
6841 » » expr = download_agent_expr (eaction->expr); | |
6842 » » write_inferior_data_ptr | |
6843 » » (ipa_action + offsetof (struct eval_expr_action, expr), | |
6844 » » expr); | |
6845 » » break; | |
6846 » } | |
6847 » case 'L': | |
6848 » ipa_action = target_malloc | |
6849 » » (sizeof (struct collect_static_trace_data_action)); | |
6850 » write_inferior_memory | |
6851 » » (ipa_action, | |
6852 » » (unsigned char *) action, | |
6853 » » sizeof (struct collect_static_trace_data_action)); | |
6854 » break; | |
6855 » default: | |
6856 » trace_debug ("unknown trace action '%c', ignoring", | |
6857 » » » action->type); | |
6858 » break; | |
6859 » } | |
6860 | 5930 |
6861 if (ipa_action != 0) | 5931 if (ipa_action != 0) |
6862 write_inferior_data_ptr | 5932 write_inferior_data_ptr |
6863 (actions_array + i * sizeof (sizeof (*tpoint->actions)), | 5933 (actions_array + i * sizeof (sizeof (*tpoint->actions)), |
6864 ipa_action); | 5934 ipa_action); |
6865 } | 5935 } |
6866 } | 5936 } |
6867 } | 5937 } |
6868 | 5938 |
| 5939 #define IPA_PROTO_FAST_TRACE_FLAG 0 |
| 5940 #define IPA_PROTO_FAST_TRACE_ADDR_ON_TARGET 2 |
| 5941 #define IPA_PROTO_FAST_TRACE_JUMP_PAD 10 |
| 5942 #define IPA_PROTO_FAST_TRACE_FJUMP_SIZE 18 |
| 5943 #define IPA_PROTO_FAST_TRACE_FJUMP_INSN 22 |
| 5944 |
| 5945 /* Send a command to agent to download and install tracepoint TPOINT. */ |
| 5946 |
| 5947 static int |
| 5948 tracepoint_send_agent (struct tracepoint *tpoint) |
| 5949 { |
| 5950 char buf[IPA_CMD_BUF_SIZE]; |
| 5951 char *p; |
| 5952 int i, ret; |
| 5953 |
| 5954 p = buf; |
| 5955 strcpy (p, "FastTrace:"); |
| 5956 p += 10; |
| 5957 |
| 5958 COPY_FIELD_TO_BUF (p, tpoint, number); |
| 5959 COPY_FIELD_TO_BUF (p, tpoint, address); |
| 5960 COPY_FIELD_TO_BUF (p, tpoint, type); |
| 5961 COPY_FIELD_TO_BUF (p, tpoint, enabled); |
| 5962 COPY_FIELD_TO_BUF (p, tpoint, step_count); |
| 5963 COPY_FIELD_TO_BUF (p, tpoint, pass_count); |
| 5964 COPY_FIELD_TO_BUF (p, tpoint, numactions); |
| 5965 COPY_FIELD_TO_BUF (p, tpoint, hit_count); |
| 5966 COPY_FIELD_TO_BUF (p, tpoint, traceframe_usage); |
| 5967 COPY_FIELD_TO_BUF (p, tpoint, compiled_cond); |
| 5968 COPY_FIELD_TO_BUF (p, tpoint, orig_size); |
| 5969 |
| 5970 /* condition */ |
| 5971 p = agent_expr_send (p, tpoint->cond); |
| 5972 |
| 5973 /* tracepoint_action */ |
| 5974 for (i = 0; i < tpoint->numactions; i++) |
| 5975 { |
| 5976 struct tracepoint_action *action = tpoint->actions[i]; |
| 5977 |
| 5978 p[0] = action->type; |
| 5979 p = action->ops->send (&p[1], action); |
| 5980 } |
| 5981 |
| 5982 get_jump_space_head (); |
| 5983 /* Copy the value of GDB_JUMP_PAD_HEAD to command buffer, so that |
| 5984 agent can use jump pad from it. */ |
| 5985 if (tpoint->type == fast_tracepoint) |
| 5986 { |
| 5987 memcpy (p, &gdb_jump_pad_head, 8); |
| 5988 p += 8; |
| 5989 } |
| 5990 |
| 5991 ret = run_inferior_command (buf, (int) (ptrdiff_t) (p - buf)); |
| 5992 if (ret) |
| 5993 return ret; |
| 5994 |
| 5995 if (strncmp (buf, "OK", 2) != 0) |
| 5996 return 1; |
| 5997 |
| 5998 /* The value of tracepoint's target address is stored in BUF. */ |
| 5999 memcpy (&tpoint->obj_addr_on_target, |
| 6000 &buf[IPA_PROTO_FAST_TRACE_ADDR_ON_TARGET], 8); |
| 6001 |
| 6002 if (tpoint->type == fast_tracepoint) |
| 6003 { |
| 6004 unsigned char *insn |
| 6005 = (unsigned char *) &buf[IPA_PROTO_FAST_TRACE_FJUMP_INSN]; |
| 6006 int fjump_size; |
| 6007 |
| 6008 trace_debug ("agent: read from cmd_buf 0x%x 0x%x\n", |
| 6009 (unsigned int) tpoint->obj_addr_on_target, |
| 6010 (unsigned int) gdb_jump_pad_head); |
| 6011 |
| 6012 memcpy (&gdb_jump_pad_head, &buf[IPA_PROTO_FAST_TRACE_JUMP_PAD], 8); |
| 6013 |
| 6014 /* This has been done in agent. We should also set up record for it. */ |
| 6015 memcpy (&fjump_size, &buf[IPA_PROTO_FAST_TRACE_FJUMP_SIZE], 4); |
| 6016 /* Wire it in. */ |
| 6017 tpoint->handle |
| 6018 = set_fast_tracepoint_jump (tpoint->address, insn, fjump_size); |
| 6019 } |
| 6020 |
| 6021 return 0; |
| 6022 } |
| 6023 |
6869 static void | 6024 static void |
6870 download_tracepoint (struct tracepoint *tpoint) | 6025 download_tracepoint (struct tracepoint *tpoint) |
6871 { | 6026 { |
6872 struct tracepoint *tp, *tp_prev; | 6027 struct tracepoint *tp, *tp_prev; |
6873 | 6028 |
6874 if (tpoint->type != fast_tracepoint | 6029 if (tpoint->type != fast_tracepoint |
6875 && tpoint->type != static_tracepoint) | 6030 && tpoint->type != static_tracepoint) |
6876 return; | 6031 return; |
6877 | 6032 |
6878 download_tracepoint_1 (tpoint); | 6033 download_tracepoint_1 (tpoint); |
(...skipping 28 matching lines...) Expand all Loading... |
6907 } | 6062 } |
6908 else | 6063 else |
6909 /* First object in list, set the head pointer in the | 6064 /* First object in list, set the head pointer in the |
6910 inferior. */ | 6065 inferior. */ |
6911 write_inferior_data_ptr (ipa_sym_addrs.addr_tracepoints, | 6066 write_inferior_data_ptr (ipa_sym_addrs.addr_tracepoints, |
6912 tpoint->obj_addr_on_target); | 6067 tpoint->obj_addr_on_target); |
6913 | 6068 |
6914 } | 6069 } |
6915 | 6070 |
6916 static void | 6071 static void |
6917 download_tracepoints (void) | |
6918 { | |
6919 CORE_ADDR tpptr = 0, prev_tpptr = 0; | |
6920 struct tracepoint *tpoint; | |
6921 | |
6922 /* Start out empty. */ | |
6923 write_inferior_data_ptr (ipa_sym_addrs.addr_tracepoints, 0); | |
6924 | |
6925 for (tpoint = tracepoints; tpoint; tpoint = tpoint->next) | |
6926 { | |
6927 if (tpoint->type != fast_tracepoint | |
6928 && tpoint->type != static_tracepoint) | |
6929 continue; | |
6930 | |
6931 prev_tpptr = tpptr; | |
6932 | |
6933 download_tracepoint_1 (tpoint); | |
6934 | |
6935 tpptr = tpoint->obj_addr_on_target; | |
6936 | |
6937 if (tpoint == tracepoints) | |
6938 { | |
6939 /* First object in list, set the head pointer in the | |
6940 inferior. */ | |
6941 write_inferior_data_ptr (ipa_sym_addrs.addr_tracepoints, tpptr); | |
6942 } | |
6943 else | |
6944 { | |
6945 write_inferior_data_ptr (prev_tpptr + offsetof (struct tracepoint, | |
6946 next), | |
6947 tpptr); | |
6948 } | |
6949 } | |
6950 } | |
6951 | |
6952 static void | |
6953 download_trace_state_variables (void) | 6072 download_trace_state_variables (void) |
6954 { | 6073 { |
6955 CORE_ADDR ptr = 0, prev_ptr = 0; | 6074 CORE_ADDR ptr = 0, prev_ptr = 0; |
6956 struct trace_state_variable *tsv; | 6075 struct trace_state_variable *tsv; |
6957 | 6076 |
6958 /* Start out empty. */ | 6077 /* Start out empty. */ |
6959 write_inferior_data_ptr (ipa_sym_addrs.addr_trace_state_variables, 0); | 6078 write_inferior_data_ptr (ipa_sym_addrs.addr_trace_state_variables, 0); |
6960 | 6079 |
6961 for (tsv = trace_state_variables; tsv != NULL; tsv = tsv->next) | 6080 for (tsv = trace_state_variables; tsv != NULL; tsv = tsv->next) |
6962 { | 6081 { |
(...skipping 315 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7278 unpause_all (1); | 6397 unpause_all (1); |
7279 | 6398 |
7280 if (trace_buffer_is_full) | 6399 if (trace_buffer_is_full) |
7281 stop_tracing (); | 6400 stop_tracing (); |
7282 } | 6401 } |
7283 #endif | 6402 #endif |
7284 | 6403 |
7285 #ifdef IN_PROCESS_AGENT | 6404 #ifdef IN_PROCESS_AGENT |
7286 | 6405 |
7287 IP_AGENT_EXPORT int ust_loaded; | 6406 IP_AGENT_EXPORT int ust_loaded; |
7288 IP_AGENT_EXPORT char cmd_buf[CMD_BUF_SIZE]; | 6407 IP_AGENT_EXPORT char cmd_buf[IPA_CMD_BUF_SIZE]; |
7289 | 6408 |
7290 #ifdef HAVE_UST | 6409 #ifdef HAVE_UST |
7291 | 6410 |
7292 /* Static tracepoints. */ | 6411 /* Static tracepoints. */ |
7293 | 6412 |
7294 /* UST puts a "struct tracepoint" in the global namespace, which | 6413 /* UST puts a "struct tracepoint" in the global namespace, which |
7295 conflicts with our tracepoint. Arguably, being a library, it | 6414 conflicts with our tracepoint. Arguably, being a library, it |
7296 shouldn't take ownership of such a generic name. We work around it | 6415 shouldn't take ownership of such a generic name. We work around it |
7297 here. */ | 6416 here. */ |
7298 #define tracepoint ust_tracepoint | 6417 #define tracepoint ust_tracepoint |
(...skipping 172 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7471 tracing library by the user, at the time of the tracepoint marker | 6590 tracing library by the user, at the time of the tracepoint marker |
7472 call. E.g., in the UST marker call: | 6591 call. E.g., in the UST marker call: |
7473 | 6592 |
7474 trace_mark (ust, bar33, "str %s", "FOOBAZ"); | 6593 trace_mark (ust, bar33, "str %s", "FOOBAZ"); |
7475 | 6594 |
7476 the collected data is "str FOOBAZ". | 6595 the collected data is "str FOOBAZ". |
7477 */ | 6596 */ |
7478 | 6597 |
7479 static void | 6598 static void |
7480 collect_ust_data_at_tracepoint (struct tracepoint_hit_ctx *ctx, | 6599 collect_ust_data_at_tracepoint (struct tracepoint_hit_ctx *ctx, |
7481 CORE_ADDR stop_pc, | |
7482 struct tracepoint *tpoint, | |
7483 struct traceframe *tframe) | 6600 struct traceframe *tframe) |
7484 { | 6601 { |
7485 struct static_tracepoint_ctx *umd = (struct static_tracepoint_ctx *) ctx; | 6602 struct static_tracepoint_ctx *umd = (struct static_tracepoint_ctx *) ctx; |
7486 unsigned char *bufspace; | 6603 unsigned char *bufspace; |
7487 int size; | 6604 int size; |
7488 va_list copy; | 6605 va_list copy; |
7489 unsigned short blocklen; | 6606 unsigned short blocklen; |
7490 | 6607 |
7491 if (umd == NULL) | 6608 if (umd == NULL) |
7492 { | 6609 { |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7529 static struct ltt_available_probe gdb_ust_probe = | 6646 static struct ltt_available_probe gdb_ust_probe = |
7530 { | 6647 { |
7531 GDB_PROBE_NAME, | 6648 GDB_PROBE_NAME, |
7532 NULL, | 6649 NULL, |
7533 gdb_probe, | 6650 gdb_probe, |
7534 }; | 6651 }; |
7535 | 6652 |
7536 #endif /* HAVE_UST */ | 6653 #endif /* HAVE_UST */ |
7537 #endif /* IN_PROCESS_AGENT */ | 6654 #endif /* IN_PROCESS_AGENT */ |
7538 | 6655 |
7539 #ifdef HAVE_UST | |
7540 | |
7541 #include <sys/socket.h> | |
7542 #include <sys/un.h> | |
7543 | |
7544 #ifndef UNIX_PATH_MAX | |
7545 #define UNIX_PATH_MAX sizeof(((struct sockaddr_un *) NULL)->sun_path) | |
7546 #endif | |
7547 | |
7548 /* Where we put the socked used for synchronization. */ | |
7549 #define SOCK_DIR P_tmpdir | |
7550 | |
7551 #endif /* HAVE_UST */ | |
7552 | |
7553 #ifndef IN_PROCESS_AGENT | 6656 #ifndef IN_PROCESS_AGENT |
7554 | 6657 |
7555 #ifdef HAVE_UST | |
7556 | |
7557 static int | |
7558 gdb_ust_connect_sync_socket (int pid) | |
7559 { | |
7560 struct sockaddr_un addr; | |
7561 int res, fd; | |
7562 char path[UNIX_PATH_MAX]; | |
7563 | |
7564 res = xsnprintf (path, UNIX_PATH_MAX, "%s/gdb_ust%d", SOCK_DIR, pid); | |
7565 if (res >= UNIX_PATH_MAX) | |
7566 { | |
7567 trace_debug ("string overflow allocating socket name"); | |
7568 return -1; | |
7569 } | |
7570 | |
7571 res = fd = socket (PF_UNIX, SOCK_STREAM, 0); | |
7572 if (res == -1) | |
7573 { | |
7574 warning ("error opening sync socket: %s\n", strerror (errno)); | |
7575 return -1; | |
7576 } | |
7577 | |
7578 addr.sun_family = AF_UNIX; | |
7579 | |
7580 res = xsnprintf (addr.sun_path, UNIX_PATH_MAX, "%s", path); | |
7581 if (res >= UNIX_PATH_MAX) | |
7582 { | |
7583 warning ("string overflow allocating socket name\n"); | |
7584 close (fd); | |
7585 return -1; | |
7586 } | |
7587 | |
7588 res = connect (fd, (struct sockaddr *) &addr, sizeof (addr)); | |
7589 if (res == -1) | |
7590 { | |
7591 warning ("error connecting sync socket (%s): %s. " | |
7592 "Make sure the directory exists and that it is writable.", | |
7593 path, strerror (errno)); | |
7594 close (fd); | |
7595 return -1; | |
7596 } | |
7597 | |
7598 return fd; | |
7599 } | |
7600 | |
7601 /* Resume thread PTID. */ | |
7602 | |
7603 static void | |
7604 resume_thread (ptid_t ptid) | |
7605 { | |
7606 struct thread_resume resume_info; | |
7607 | |
7608 resume_info.thread = ptid; | |
7609 resume_info.kind = resume_continue; | |
7610 resume_info.sig = TARGET_SIGNAL_0; | |
7611 (*the_target->resume) (&resume_info, 1); | |
7612 } | |
7613 | |
7614 /* Stop thread PTID. */ | |
7615 | |
7616 static void | |
7617 stop_thread (ptid_t ptid) | |
7618 { | |
7619 struct thread_resume resume_info; | |
7620 | |
7621 resume_info.thread = ptid; | |
7622 resume_info.kind = resume_stop; | |
7623 resume_info.sig = TARGET_SIGNAL_0; | |
7624 (*the_target->resume) (&resume_info, 1); | |
7625 } | |
7626 | |
7627 /* Ask the in-process agent to run a command. Since we don't want to | 6658 /* Ask the in-process agent to run a command. Since we don't want to |
7628 have to handle the IPA hitting breakpoints while running the | 6659 have to handle the IPA hitting breakpoints while running the |
7629 command, we pause all threads, remove all breakpoints, and then set | 6660 command, we pause all threads, remove all breakpoints, and then set |
7630 the helper thread re-running. We communicate with the helper | 6661 the helper thread re-running. We communicate with the helper |
7631 thread by means of direct memory xfering, and a socket for | 6662 thread by means of direct memory xfering, and a socket for |
7632 synchronization. */ | 6663 synchronization. */ |
7633 | 6664 |
7634 static int | 6665 static int |
7635 run_inferior_command (char *cmd) | 6666 run_inferior_command (char *cmd, int len) |
7636 { | 6667 { |
7637 int err = -1; | 6668 int err = -1; |
7638 int fd = -1; | |
7639 int pid = ptid_get_pid (current_inferior->entry.id); | 6669 int pid = ptid_get_pid (current_inferior->entry.id); |
7640 int tid; | |
7641 ptid_t ptid = null_ptid; | |
7642 | 6670 |
7643 trace_debug ("run_inferior_command: running: %s", cmd); | 6671 trace_debug ("run_inferior_command: running: %s", cmd); |
7644 | 6672 |
7645 pause_all (0); | 6673 pause_all (0); |
7646 uninsert_all_breakpoints (); | 6674 uninsert_all_breakpoints (); |
7647 | 6675 |
7648 if (read_inferior_integer (ipa_sym_addrs.addr_helper_thread_id, &tid)) | 6676 err = agent_run_command (pid, (const char *) cmd, len); |
7649 { | |
7650 warning ("Error reading helper thread's id in lib"); | |
7651 goto out; | |
7652 } | |
7653 | |
7654 if (tid == 0) | |
7655 { | |
7656 warning ("helper thread not initialized yet"); | |
7657 goto out; | |
7658 } | |
7659 | |
7660 if (write_inferior_memory (ipa_sym_addrs.addr_cmd_buf, | |
7661 » » » (unsigned char *) cmd, strlen (cmd) + 1)) | |
7662 { | |
7663 warning ("Error writing command"); | |
7664 goto out; | |
7665 } | |
7666 | |
7667 ptid = ptid_build (pid, tid, 0); | |
7668 | |
7669 resume_thread (ptid); | |
7670 | |
7671 fd = gdb_ust_connect_sync_socket (pid); | |
7672 if (fd >= 0) | |
7673 { | |
7674 char buf[1] = ""; | |
7675 int ret; | |
7676 | |
7677 trace_debug ("signalling helper thread"); | |
7678 | |
7679 do | |
7680 » { | |
7681 » ret = write (fd, buf, 1); | |
7682 » } while (ret == -1 && errno == EINTR); | |
7683 | |
7684 trace_debug ("waiting for helper thread's response"); | |
7685 | |
7686 do | |
7687 » { | |
7688 » ret = read (fd, buf, 1); | |
7689 » } while (ret == -1 && errno == EINTR); | |
7690 | |
7691 close (fd); | |
7692 | |
7693 trace_debug ("helper thread's response received"); | |
7694 } | |
7695 | |
7696 out: | |
7697 | |
7698 /* Need to read response with the inferior stopped. */ | |
7699 if (!ptid_equal (ptid, null_ptid)) | |
7700 { | |
7701 int was_non_stop = non_stop; | |
7702 struct target_waitstatus status; | |
7703 | |
7704 stop_thread (ptid); | |
7705 non_stop = 1; | |
7706 mywait (ptid, &status, 0, 0); | |
7707 non_stop = was_non_stop; | |
7708 } | |
7709 | |
7710 if (fd >= 0) | |
7711 { | |
7712 if (read_inferior_memory (ipa_sym_addrs.addr_cmd_buf, | |
7713 » » » » (unsigned char *) cmd, CMD_BUF_SIZE)) | |
7714 » { | |
7715 » warning ("Error reading command response"); | |
7716 » } | |
7717 else | |
7718 » { | |
7719 » err = 0; | |
7720 » trace_debug ("run_inferior_command: response: %s", cmd); | |
7721 » } | |
7722 } | |
7723 | 6677 |
7724 reinsert_all_breakpoints (); | 6678 reinsert_all_breakpoints (); |
7725 unpause_all (0); | 6679 unpause_all (0); |
7726 | 6680 |
7727 return err; | 6681 return err; |
7728 } | 6682 } |
7729 | 6683 |
7730 #else /* HAVE_UST */ | 6684 #else /* !IN_PROCESS_AGENT */ |
7731 | 6685 |
7732 static int | 6686 #include <sys/socket.h> |
7733 run_inferior_command (char *cmd) | 6687 #include <sys/un.h> |
7734 { | |
7735 return -1; | |
7736 } | |
7737 | 6688 |
7738 #endif /* HAVE_UST */ | 6689 #ifndef UNIX_PATH_MAX |
| 6690 #define UNIX_PATH_MAX sizeof(((struct sockaddr_un *) NULL)->sun_path) |
| 6691 #endif |
7739 | 6692 |
7740 #else /* !IN_PROCESS_AGENT */ | 6693 /* Where we put the socked used for synchronization. */ |
| 6694 #define SOCK_DIR P_tmpdir |
7741 | 6695 |
7742 /* Thread ID of the helper thread. GDBserver reads this to know which | 6696 /* Thread ID of the helper thread. GDBserver reads this to know which |
7743 is the help thread. This is an LWP id on Linux. */ | 6697 is the help thread. This is an LWP id on Linux. */ |
7744 int helper_thread_id; | 6698 int helper_thread_id; |
7745 | 6699 |
7746 #ifdef HAVE_UST | |
7747 | |
7748 static int | 6700 static int |
7749 init_named_socket (const char *name) | 6701 init_named_socket (const char *name) |
7750 { | 6702 { |
7751 int result, fd; | 6703 int result, fd; |
7752 struct sockaddr_un addr; | 6704 struct sockaddr_un addr; |
7753 | 6705 |
7754 result = fd = socket (PF_UNIX, SOCK_STREAM, 0); | 6706 result = fd = socket (PF_UNIX, SOCK_STREAM, 0); |
7755 if (result == -1) | 6707 if (result == -1) |
7756 { | 6708 { |
7757 warning ("socket creation failed: %s", strerror (errno)); | 6709 warning ("socket creation failed: %s", strerror (errno)); |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7790 { | 6742 { |
7791 warning ("listen: %s", strerror (errno)); | 6743 warning ("listen: %s", strerror (errno)); |
7792 close (fd); | 6744 close (fd); |
7793 return -1; | 6745 return -1; |
7794 } | 6746 } |
7795 | 6747 |
7796 return fd; | 6748 return fd; |
7797 } | 6749 } |
7798 | 6750 |
7799 static int | 6751 static int |
7800 gdb_ust_socket_init (void) | 6752 gdb_agent_socket_init (void) |
7801 { | 6753 { |
7802 int result, fd; | 6754 int result, fd; |
7803 char name[UNIX_PATH_MAX]; | 6755 char name[UNIX_PATH_MAX]; |
7804 | 6756 |
7805 result = xsnprintf (name, UNIX_PATH_MAX, "%s/gdb_ust%d", | 6757 result = xsnprintf (name, UNIX_PATH_MAX, "%s/gdb_ust%d", |
7806 SOCK_DIR, getpid ()); | 6758 SOCK_DIR, getpid ()); |
7807 if (result >= UNIX_PATH_MAX) | 6759 if (result >= UNIX_PATH_MAX) |
7808 { | 6760 { |
7809 trace_debug ("string overflow allocating socket name"); | 6761 trace_debug ("string overflow allocating socket name"); |
7810 return -1; | 6762 return -1; |
7811 } | 6763 } |
7812 | 6764 |
7813 fd = init_named_socket (name); | 6765 fd = init_named_socket (name); |
7814 if (fd < 0) | 6766 if (fd < 0) |
7815 warning ("Error initializing named socket (%s) for communication with the " | 6767 warning ("Error initializing named socket (%s) for communication with the " |
7816 "ust helper thread. Check that directory exists and that it " | 6768 "ust helper thread. Check that directory exists and that it " |
7817 "is writable.", name); | 6769 "is writable.", name); |
7818 | 6770 |
7819 return fd; | 6771 return fd; |
7820 } | 6772 } |
7821 | 6773 |
7822 /* Return an hexstr version of the STR C string, fit for sending to | 6774 #ifdef HAVE_UST |
7823 GDB. */ | |
7824 | |
7825 static char * | |
7826 cstr_to_hexstr (const char *str) | |
7827 { | |
7828 int len = strlen (str); | |
7829 char *hexstr = xmalloc (len * 2 + 1); | |
7830 convert_int_to_ascii ((gdb_byte *) str, hexstr, len); | |
7831 return hexstr; | |
7832 } | |
7833 | 6775 |
7834 /* The next marker to be returned on a qTsSTM command. */ | 6776 /* The next marker to be returned on a qTsSTM command. */ |
7835 static const struct marker *next_st; | 6777 static const struct marker *next_st; |
7836 | 6778 |
7837 /* Returns the first known marker. */ | 6779 /* Returns the first known marker. */ |
7838 | 6780 |
7839 struct marker * | 6781 struct marker * |
7840 first_marker (void) | 6782 first_marker (void) |
7841 { | 6783 { |
7842 struct marker_iter iter; | 6784 struct marker_iter iter; |
(...skipping 19 matching lines...) Expand all Loading... |
7862 if (iter.marker == m) | 6804 if (iter.marker == m) |
7863 { | 6805 { |
7864 USTF(marker_iter_next) (&iter); | 6806 USTF(marker_iter_next) (&iter); |
7865 return iter.marker; | 6807 return iter.marker; |
7866 } | 6808 } |
7867 } | 6809 } |
7868 | 6810 |
7869 return NULL; | 6811 return NULL; |
7870 } | 6812 } |
7871 | 6813 |
| 6814 /* Return an hexstr version of the STR C string, fit for sending to |
| 6815 GDB. */ |
| 6816 |
| 6817 static char * |
| 6818 cstr_to_hexstr (const char *str) |
| 6819 { |
| 6820 int len = strlen (str); |
| 6821 char *hexstr = xmalloc (len * 2 + 1); |
| 6822 convert_int_to_ascii ((gdb_byte *) str, hexstr, len); |
| 6823 return hexstr; |
| 6824 } |
| 6825 |
7872 /* Compose packet that is the response to the qTsSTM/qTfSTM/qTSTMat | 6826 /* Compose packet that is the response to the qTsSTM/qTfSTM/qTSTMat |
7873 packets. */ | 6827 packets. */ |
7874 | 6828 |
7875 static void | 6829 static void |
7876 response_ust_marker (char *packet, const struct marker *st) | 6830 response_ust_marker (char *packet, const struct marker *st) |
7877 { | 6831 { |
7878 char *strid, *format, *tmp; | 6832 char *strid, *format, *tmp; |
7879 | 6833 |
7880 next_st = next_marker (st); | 6834 next_st = next_marker (st); |
7881 | 6835 |
(...skipping 140 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
8022 if ((uintptr_t ) m->location == address) | 6976 if ((uintptr_t ) m->location == address) |
8023 { | 6977 { |
8024 response_ust_marker (packet, m); | 6978 response_ust_marker (packet, m); |
8025 return 0; | 6979 return 0; |
8026 } | 6980 } |
8027 | 6981 |
8028 strcpy (packet, "l"); | 6982 strcpy (packet, "l"); |
8029 return -1; | 6983 return -1; |
8030 } | 6984 } |
8031 | 6985 |
| 6986 static void |
| 6987 gdb_ust_init (void) |
| 6988 { |
| 6989 if (!dlsym_ust ()) |
| 6990 return; |
| 6991 |
| 6992 USTF(ltt_probe_register) (&gdb_ust_probe); |
| 6993 } |
| 6994 |
| 6995 #endif /* HAVE_UST */ |
| 6996 |
| 6997 #include <sys/syscall.h> |
| 6998 |
| 6999 /* Helper thread of agent. */ |
| 7000 |
8032 static void * | 7001 static void * |
8033 gdb_ust_thread (void *arg) | 7002 gdb_agent_helper_thread (void *arg) |
8034 { | 7003 { |
8035 int listen_fd; | 7004 int listen_fd; |
8036 | 7005 |
8037 while (1) | 7006 while (1) |
8038 { | 7007 { |
8039 listen_fd = gdb_ust_socket_init (); | 7008 listen_fd = gdb_agent_socket_init (); |
8040 | 7009 |
8041 #ifdef SYS_gettid | |
8042 if (helper_thread_id == 0) | 7010 if (helper_thread_id == 0) |
8043 helper_thread_id = syscall (SYS_gettid); | 7011 helper_thread_id = syscall (SYS_gettid); |
8044 #endif | |
8045 | 7012 |
8046 if (listen_fd == -1) | 7013 if (listen_fd == -1) |
8047 { | 7014 { |
8048 warning ("could not create sync socket\n"); | 7015 warning ("could not create sync socket\n"); |
8049 break; | 7016 break; |
8050 } | 7017 } |
8051 | 7018 |
8052 while (1) | 7019 while (1) |
8053 { | 7020 { |
8054 socklen_t tmp; | 7021 socklen_t tmp; |
(...skipping 26 matching lines...) Expand all Loading... |
8081 if (ret == -1) | 7048 if (ret == -1) |
8082 { | 7049 { |
8083 warning ("reading socket (fd=%d) failed with %s", | 7050 warning ("reading socket (fd=%d) failed with %s", |
8084 fd, strerror (errno)); | 7051 fd, strerror (errno)); |
8085 close (fd); | 7052 close (fd); |
8086 break; | 7053 break; |
8087 } | 7054 } |
8088 | 7055 |
8089 if (cmd_buf[0]) | 7056 if (cmd_buf[0]) |
8090 { | 7057 { |
| 7058 #ifdef HAVE_UST |
8091 if (strcmp ("qTfSTM", cmd_buf) == 0) | 7059 if (strcmp ("qTfSTM", cmd_buf) == 0) |
8092 { | 7060 { |
8093 cmd_qtfstm (cmd_buf); | 7061 cmd_qtfstm (cmd_buf); |
8094 } | 7062 } |
8095 else if (strcmp ("qTsSTM", cmd_buf) == 0) | 7063 else if (strcmp ("qTsSTM", cmd_buf) == 0) |
8096 { | 7064 { |
8097 cmd_qtsstm (cmd_buf); | 7065 cmd_qtsstm (cmd_buf); |
8098 } | 7066 } |
8099 else if (strncmp ("unprobe_marker_at:", | 7067 else if (strncmp ("unprobe_marker_at:", |
8100 cmd_buf, | 7068 cmd_buf, |
8101 sizeof ("unprobe_marker_at:") - 1) == 0) | 7069 sizeof ("unprobe_marker_at:") - 1) == 0) |
8102 { | 7070 { |
8103 unprobe_marker_at (cmd_buf); | 7071 unprobe_marker_at (cmd_buf); |
8104 } | 7072 } |
8105 else if (strncmp ("probe_marker_at:", | 7073 else if (strncmp ("probe_marker_at:", |
8106 cmd_buf, | 7074 cmd_buf, |
8107 sizeof ("probe_marker_at:") - 1) == 0) | 7075 sizeof ("probe_marker_at:") - 1) == 0) |
8108 { | 7076 { |
8109 probe_marker_at (cmd_buf); | 7077 probe_marker_at (cmd_buf); |
8110 } | 7078 } |
8111 else if (strncmp ("qTSTMat:", | 7079 else if (strncmp ("qTSTMat:", |
8112 cmd_buf, | 7080 cmd_buf, |
8113 sizeof ("qTSTMat:") - 1) == 0) | 7081 sizeof ("qTSTMat:") - 1) == 0) |
8114 { | 7082 { |
8115 cmd_qtstmat (cmd_buf); | 7083 cmd_qtstmat (cmd_buf); |
8116 } | 7084 } |
8117 » else if (strcmp (cmd_buf, "help") == 0) | 7085 #endif /* HAVE_UST */ |
8118 » » { | |
8119 » » strcpy (cmd_buf, "for help, press F1\n"); | |
8120 » » } | |
8121 » else | |
8122 » » strcpy (cmd_buf, ""); | |
8123 } | 7086 } |
8124 | 7087 |
8125 » write (fd, buf, 1); | 7088 » /* Fix compiler's warning: ignoring return value of 'write'. */ |
| 7089 » ret = write (fd, buf, 1); |
8126 close (fd); | 7090 close (fd); |
8127 } | 7091 } |
8128 } | 7092 } |
8129 | 7093 |
8130 return NULL; | 7094 return NULL; |
8131 } | 7095 } |
8132 | 7096 |
8133 #include <signal.h> | 7097 #include <signal.h> |
| 7098 #include <pthread.h> |
| 7099 |
| 7100 IP_AGENT_EXPORT int gdb_agent_capability = AGENT_CAPA_STATIC_TRACE; |
8134 | 7101 |
8135 static void | 7102 static void |
8136 gdb_ust_init (void) | 7103 gdb_agent_init (void) |
8137 { | 7104 { |
8138 int res; | 7105 int res; |
8139 pthread_t thread; | 7106 pthread_t thread; |
8140 sigset_t new_mask; | 7107 sigset_t new_mask; |
8141 sigset_t orig_mask; | 7108 sigset_t orig_mask; |
8142 | 7109 |
8143 if (!dlsym_ust ()) | |
8144 return; | |
8145 | |
8146 /* We want the helper thread to be as transparent as possible, so | 7110 /* We want the helper thread to be as transparent as possible, so |
8147 have it inherit an all-signals-blocked mask. */ | 7111 have it inherit an all-signals-blocked mask. */ |
8148 | 7112 |
8149 sigfillset (&new_mask); | 7113 sigfillset (&new_mask); |
8150 res = pthread_sigmask (SIG_SETMASK, &new_mask, &orig_mask); | 7114 res = pthread_sigmask (SIG_SETMASK, &new_mask, &orig_mask); |
8151 if (res) | 7115 if (res) |
8152 fatal ("pthread_sigmask (1) failed: %s", strerror (res)); | 7116 fatal ("pthread_sigmask (1) failed: %s", strerror (res)); |
8153 | 7117 |
8154 res = pthread_create (&thread, | 7118 res = pthread_create (&thread, |
8155 NULL, | 7119 NULL, |
8156 » » » gdb_ust_thread, | 7120 » » » gdb_agent_helper_thread, |
8157 NULL); | 7121 NULL); |
8158 | 7122 |
8159 res = pthread_sigmask (SIG_SETMASK, &orig_mask, NULL); | 7123 res = pthread_sigmask (SIG_SETMASK, &orig_mask, NULL); |
8160 if (res) | 7124 if (res) |
8161 fatal ("pthread_sigmask (2) failed: %s", strerror (res)); | 7125 fatal ("pthread_sigmask (2) failed: %s", strerror (res)); |
8162 | 7126 |
8163 while (helper_thread_id == 0) | 7127 while (helper_thread_id == 0) |
8164 usleep (1); | 7128 usleep (1); |
8165 | 7129 |
8166 USTF(ltt_probe_register) (&gdb_ust_probe); | 7130 #ifdef HAVE_UST |
| 7131 gdb_ust_init (); |
| 7132 #endif |
8167 } | 7133 } |
8168 | 7134 |
8169 #endif /* HAVE_UST */ | |
8170 | |
8171 #include <sys/mman.h> | 7135 #include <sys/mman.h> |
8172 #include <fcntl.h> | 7136 #include <fcntl.h> |
8173 | 7137 |
8174 IP_AGENT_EXPORT char *gdb_tp_heap_buffer; | 7138 IP_AGENT_EXPORT char *gdb_tp_heap_buffer; |
8175 IP_AGENT_EXPORT char *gdb_jump_pad_buffer; | 7139 IP_AGENT_EXPORT char *gdb_jump_pad_buffer; |
8176 IP_AGENT_EXPORT char *gdb_jump_pad_buffer_end; | 7140 IP_AGENT_EXPORT char *gdb_jump_pad_buffer_end; |
8177 IP_AGENT_EXPORT char *gdb_trampoline_buffer; | 7141 IP_AGENT_EXPORT char *gdb_trampoline_buffer; |
8178 IP_AGENT_EXPORT char *gdb_trampoline_buffer_end; | 7142 IP_AGENT_EXPORT char *gdb_trampoline_buffer_end; |
8179 IP_AGENT_EXPORT char *gdb_trampoline_buffer_error; | 7143 IP_AGENT_EXPORT char *gdb_trampoline_buffer_error; |
8180 | 7144 |
(...skipping 10 matching lines...) Expand all Loading... |
8191 strncpy (gdb_trampoline_buffer_error, errmsg, 99); | 7155 strncpy (gdb_trampoline_buffer_error, errmsg, 99); |
8192 else | 7156 else |
8193 strcpy (gdb_trampoline_buffer_error, "no buffer passed"); | 7157 strcpy (gdb_trampoline_buffer_error, "no buffer passed"); |
8194 } | 7158 } |
8195 | 7159 |
8196 static void __attribute__ ((constructor)) | 7160 static void __attribute__ ((constructor)) |
8197 initialize_tracepoint_ftlib (void) | 7161 initialize_tracepoint_ftlib (void) |
8198 { | 7162 { |
8199 initialize_tracepoint (); | 7163 initialize_tracepoint (); |
8200 | 7164 |
8201 #ifdef HAVE_UST | 7165 gdb_agent_init (); |
8202 gdb_ust_init (); | |
8203 #endif | |
8204 } | 7166 } |
8205 | 7167 |
8206 #endif /* IN_PROCESS_AGENT */ | 7168 #endif /* IN_PROCESS_AGENT */ |
8207 | 7169 |
8208 /* Return a timestamp, expressed as microseconds of the usual Unix | 7170 /* Return a timestamp, expressed as microseconds of the usual Unix |
8209 time. (As the result is a 64-bit number, it will not overflow any | 7171 time. (As the result is a 64-bit number, it will not overflow any |
8210 time soon.) */ | 7172 time soon.) */ |
8211 | 7173 |
8212 static LONGEST | 7174 static LONGEST |
8213 get_timestamp (void) | 7175 get_timestamp (void) |
(...skipping 17 matching lines...) Expand all Loading... |
8231 /* Wire trace state variable 1 to be the timestamp. This will be | 7193 /* Wire trace state variable 1 to be the timestamp. This will be |
8232 uploaded to GDB upon connection and become one of its trace state | 7194 uploaded to GDB upon connection and become one of its trace state |
8233 variables. (In case you're wondering, if GDB already has a trace | 7195 variables. (In case you're wondering, if GDB already has a trace |
8234 variable numbered 1, it will be renumbered.) */ | 7196 variable numbered 1, it will be renumbered.) */ |
8235 create_trace_state_variable (1, 0); | 7197 create_trace_state_variable (1, 0); |
8236 set_trace_state_variable_name (1, "trace_timestamp"); | 7198 set_trace_state_variable_name (1, "trace_timestamp"); |
8237 set_trace_state_variable_getter (1, get_timestamp); | 7199 set_trace_state_variable_getter (1, get_timestamp); |
8238 | 7200 |
8239 #ifdef IN_PROCESS_AGENT | 7201 #ifdef IN_PROCESS_AGENT |
8240 { | 7202 { |
| 7203 uintptr_t addr; |
8241 int pagesize; | 7204 int pagesize; |
| 7205 |
8242 pagesize = sysconf (_SC_PAGE_SIZE); | 7206 pagesize = sysconf (_SC_PAGE_SIZE); |
8243 if (pagesize == -1) | 7207 if (pagesize == -1) |
8244 fatal ("sysconf"); | 7208 fatal ("sysconf"); |
8245 | 7209 |
8246 gdb_tp_heap_buffer = xmalloc (5 * 1024 * 1024); | 7210 gdb_tp_heap_buffer = xmalloc (5 * 1024 * 1024); |
8247 | 7211 |
8248 /* Allocate scratch buffer aligned on a page boundary. */ | 7212 #define SCRATCH_BUFFER_NPAGES 20 |
8249 gdb_jump_pad_buffer = memalign (pagesize, pagesize * 20); | |
8250 gdb_jump_pad_buffer_end = gdb_jump_pad_buffer + pagesize * 20; | |
8251 | 7213 |
8252 /* Make it writable and executable. */ | 7214 /* Allocate scratch buffer aligned on a page boundary, at a low |
8253 if (mprotect (gdb_jump_pad_buffer, pagesize * 20, | 7215 address (close to the main executable's code). */ |
8254 » » PROT_READ | PROT_WRITE | PROT_EXEC) != 0) | 7216 for (addr = pagesize; addr != 0; addr += pagesize) |
| 7217 { |
| 7218 » gdb_jump_pad_buffer = mmap ((void *) addr, pagesize * SCRATCH_BUFFER_NPA
GES, |
| 7219 » » » » PROT_READ | PROT_WRITE | PROT_EXEC, |
| 7220 » » » » MAP_PRIVATE | MAP_ANONYMOUS | MAP_FIXED, |
| 7221 » » » » -1, 0); |
| 7222 » if (gdb_jump_pad_buffer != MAP_FAILED) |
| 7223 » break; |
| 7224 } |
| 7225 |
| 7226 if (addr == 0) |
8255 fatal ("\ | 7227 fatal ("\ |
8256 initialize_tracepoint: mprotect(%p, %d, PROT_READ|PROT_EXEC) failed with %s", | 7228 initialize_tracepoint: mmap'ing jump pad buffer failed with %s", |
8257 » gdb_jump_pad_buffer, pagesize * 20, strerror (errno)); | 7229 » strerror (errno)); |
| 7230 |
| 7231 gdb_jump_pad_buffer_end = gdb_jump_pad_buffer + pagesize * SCRATCH_BUFFER_NP
AGES; |
8258 } | 7232 } |
8259 | 7233 |
8260 gdb_trampoline_buffer = gdb_trampoline_buffer_end = 0; | 7234 gdb_trampoline_buffer = gdb_trampoline_buffer_end = 0; |
8261 | 7235 |
8262 /* It's not a fatal error for something to go wrong with trampoline | 7236 /* It's not a fatal error for something to go wrong with trampoline |
8263 buffer setup, but it can be mysterious, so create a channel to | 7237 buffer setup, but it can be mysterious, so create a channel to |
8264 report back on what went wrong, using a fixed size since we may | 7238 report back on what went wrong, using a fixed size since we may |
8265 not be able to allocate space later when the problem occurs. */ | 7239 not be able to allocate space later when the problem occurs. */ |
8266 gdb_trampoline_buffer_error = xmalloc (IPA_BUFSIZ); | 7240 gdb_trampoline_buffer_error = xmalloc (IPA_BUFSIZ); |
8267 | 7241 |
8268 strcpy (gdb_trampoline_buffer_error, "No errors reported"); | 7242 strcpy (gdb_trampoline_buffer_error, "No errors reported"); |
8269 | 7243 |
8270 initialize_low_tracepoint (); | 7244 initialize_low_tracepoint (); |
8271 #endif | 7245 #endif |
8272 } | 7246 } |
OLD | NEW |