GDB (API)
|
00001 /* Process record and replay target for GDB, the GNU debugger. 00002 00003 Copyright (C) 2013 Free Software Foundation, Inc. 00004 00005 This file is part of GDB. 00006 00007 This program is free software; you can redistribute it and/or modify 00008 it under the terms of the GNU General Public License as published by 00009 the Free Software Foundation; either version 3 of the License, or 00010 (at your option) any later version. 00011 00012 This program is distributed in the hope that it will be useful, 00013 but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00015 GNU General Public License for more details. 00016 00017 You should have received a copy of the GNU General Public License 00018 along with this program. If not, see <http://www.gnu.org/licenses/>. */ 00019 00020 #include "defs.h" 00021 #include "gdbcmd.h" 00022 #include "regcache.h" 00023 #include "gdbthread.h" 00024 #include "event-top.h" 00025 #include "exceptions.h" 00026 #include "completer.h" 00027 #include "arch-utils.h" 00028 #include "gdbcore.h" 00029 #include "exec.h" 00030 #include "record.h" 00031 #include "record-full.h" 00032 #include "elf-bfd.h" 00033 #include "gcore.h" 00034 #include "event-loop.h" 00035 #include "inf-loop.h" 00036 #include "gdb_bfd.h" 00037 #include "observer.h" 00038 00039 #include <signal.h> 00040 00041 /* This module implements "target record-full", also known as "process 00042 record and replay". This target sits on top of a "normal" target 00043 (a target that "has execution"), and provides a record and replay 00044 functionality, including reverse debugging. 00045 00046 Target record has two modes: recording, and replaying. 00047 00048 In record mode, we intercept the to_resume and to_wait methods. 00049 Whenever gdb resumes the target, we run the target in single step 00050 mode, and we build up an execution log in which, for each executed 00051 instruction, we record all changes in memory and register state. 00052 This is invisible to the user, to whom it just looks like an 00053 ordinary debugging session (except for performance degredation). 00054 00055 In replay mode, instead of actually letting the inferior run as a 00056 process, we simulate its execution by playing back the recorded 00057 execution log. For each instruction in the log, we simulate the 00058 instruction's side effects by duplicating the changes that it would 00059 have made on memory and registers. */ 00060 00061 #define DEFAULT_RECORD_FULL_INSN_MAX_NUM 200000 00062 00063 #define RECORD_FULL_IS_REPLAY \ 00064 (record_full_list->next || execution_direction == EXEC_REVERSE) 00065 00066 #define RECORD_FULL_FILE_MAGIC netorder32(0x20091016) 00067 00068 /* These are the core structs of the process record functionality. 00069 00070 A record_full_entry is a record of the value change of a register 00071 ("record_full_reg") or a part of memory ("record_full_mem"). And each 00072 instruction must have a struct record_full_entry ("record_full_end") 00073 that indicates that this is the last struct record_full_entry of this 00074 instruction. 00075 00076 Each struct record_full_entry is linked to "record_full_list" by "prev" 00077 and "next" pointers. */ 00078 00079 struct record_full_mem_entry 00080 { 00081 CORE_ADDR addr; 00082 int len; 00083 /* Set this flag if target memory for this entry 00084 can no longer be accessed. */ 00085 int mem_entry_not_accessible; 00086 union 00087 { 00088 gdb_byte *ptr; 00089 gdb_byte buf[sizeof (gdb_byte *)]; 00090 } u; 00091 }; 00092 00093 struct record_full_reg_entry 00094 { 00095 unsigned short num; 00096 unsigned short len; 00097 union 00098 { 00099 gdb_byte *ptr; 00100 gdb_byte buf[2 * sizeof (gdb_byte *)]; 00101 } u; 00102 }; 00103 00104 struct record_full_end_entry 00105 { 00106 enum gdb_signal sigval; 00107 ULONGEST insn_num; 00108 }; 00109 00110 enum record_full_type 00111 { 00112 record_full_end = 0, 00113 record_full_reg, 00114 record_full_mem 00115 }; 00116 00117 /* This is the data structure that makes up the execution log. 00118 00119 The execution log consists of a single linked list of entries 00120 of type "struct record_full_entry". It is doubly linked so that it 00121 can be traversed in either direction. 00122 00123 The start of the list is anchored by a struct called 00124 "record_full_first". The pointer "record_full_list" either points 00125 to the last entry that was added to the list (in record mode), or to 00126 the next entry in the list that will be executed (in replay mode). 00127 00128 Each list element (struct record_full_entry), in addition to next 00129 and prev pointers, consists of a union of three entry types: mem, 00130 reg, and end. A field called "type" determines which entry type is 00131 represented by a given list element. 00132 00133 Each instruction that is added to the execution log is represented 00134 by a variable number of list elements ('entries'). The instruction 00135 will have one "reg" entry for each register that is changed by 00136 executing the instruction (including the PC in every case). It 00137 will also have one "mem" entry for each memory change. Finally, 00138 each instruction will have an "end" entry that separates it from 00139 the changes associated with the next instruction. */ 00140 00141 struct record_full_entry 00142 { 00143 struct record_full_entry *prev; 00144 struct record_full_entry *next; 00145 enum record_full_type type; 00146 union 00147 { 00148 /* reg */ 00149 struct record_full_reg_entry reg; 00150 /* mem */ 00151 struct record_full_mem_entry mem; 00152 /* end */ 00153 struct record_full_end_entry end; 00154 } u; 00155 }; 00156 00157 /* If true, query if PREC cannot record memory 00158 change of next instruction. */ 00159 int record_full_memory_query = 0; 00160 00161 struct record_full_core_buf_entry 00162 { 00163 struct record_full_core_buf_entry *prev; 00164 struct target_section *p; 00165 bfd_byte *buf; 00166 }; 00167 00168 /* Record buf with core target. */ 00169 static gdb_byte *record_full_core_regbuf = NULL; 00170 static struct target_section *record_full_core_start; 00171 static struct target_section *record_full_core_end; 00172 static struct record_full_core_buf_entry *record_full_core_buf_list = NULL; 00173 00174 /* The following variables are used for managing the linked list that 00175 represents the execution log. 00176 00177 record_full_first is the anchor that holds down the beginning of 00178 the list. 00179 00180 record_full_list serves two functions: 00181 1) In record mode, it anchors the end of the list. 00182 2) In replay mode, it traverses the list and points to 00183 the next instruction that must be emulated. 00184 00185 record_full_arch_list_head and record_full_arch_list_tail are used 00186 to manage a separate list, which is used to build up the change 00187 elements of the currently executing instruction during record mode. 00188 When this instruction has been completely annotated in the "arch 00189 list", it will be appended to the main execution log. */ 00190 00191 static struct record_full_entry record_full_first; 00192 static struct record_full_entry *record_full_list = &record_full_first; 00193 static struct record_full_entry *record_full_arch_list_head = NULL; 00194 static struct record_full_entry *record_full_arch_list_tail = NULL; 00195 00196 /* 1 ask user. 0 auto delete the last struct record_full_entry. */ 00197 static int record_full_stop_at_limit = 1; 00198 /* Maximum allowed number of insns in execution log. */ 00199 static unsigned int record_full_insn_max_num 00200 = DEFAULT_RECORD_FULL_INSN_MAX_NUM; 00201 /* Actual count of insns presently in execution log. */ 00202 static unsigned int record_full_insn_num = 0; 00203 /* Count of insns logged so far (may be larger 00204 than count of insns presently in execution log). */ 00205 static ULONGEST record_full_insn_count; 00206 00207 /* The target_ops of process record. */ 00208 static struct target_ops record_full_ops; 00209 static struct target_ops record_full_core_ops; 00210 00211 /* Command lists for "set/show record full". */ 00212 static struct cmd_list_element *set_record_full_cmdlist; 00213 static struct cmd_list_element *show_record_full_cmdlist; 00214 00215 /* Command list for "record full". */ 00216 static struct cmd_list_element *record_full_cmdlist; 00217 00218 /* The beneath function pointers. */ 00219 static struct target_ops *record_full_beneath_to_resume_ops; 00220 static void (*record_full_beneath_to_resume) (struct target_ops *, ptid_t, int, 00221 enum gdb_signal); 00222 static struct target_ops *record_full_beneath_to_wait_ops; 00223 static ptid_t (*record_full_beneath_to_wait) (struct target_ops *, ptid_t, 00224 struct target_waitstatus *, 00225 int); 00226 static struct target_ops *record_full_beneath_to_store_registers_ops; 00227 static void (*record_full_beneath_to_store_registers) (struct target_ops *, 00228 struct regcache *, 00229 int regno); 00230 static struct target_ops *record_full_beneath_to_xfer_partial_ops; 00231 static LONGEST 00232 (*record_full_beneath_to_xfer_partial) (struct target_ops *ops, 00233 enum target_object object, 00234 const char *annex, 00235 gdb_byte *readbuf, 00236 const gdb_byte *writebuf, 00237 ULONGEST offset, 00238 LONGEST len); 00239 static int 00240 (*record_full_beneath_to_insert_breakpoint) (struct gdbarch *, 00241 struct bp_target_info *); 00242 static int 00243 (*record_full_beneath_to_remove_breakpoint) (struct gdbarch *, 00244 struct bp_target_info *); 00245 static int (*record_full_beneath_to_stopped_by_watchpoint) (void); 00246 static int (*record_full_beneath_to_stopped_data_address) (struct target_ops *, 00247 CORE_ADDR *); 00248 static void 00249 (*record_full_beneath_to_async) (void (*) (enum inferior_event_type, void *), 00250 void *); 00251 00252 static void record_full_goto_insn (struct record_full_entry *entry, 00253 enum exec_direction_kind dir); 00254 static void record_full_save (const char *recfilename); 00255 00256 /* Alloc and free functions for record_full_reg, record_full_mem, and 00257 record_full_end entries. */ 00258 00259 /* Alloc a record_full_reg record entry. */ 00260 00261 static inline struct record_full_entry * 00262 record_full_reg_alloc (struct regcache *regcache, int regnum) 00263 { 00264 struct record_full_entry *rec; 00265 struct gdbarch *gdbarch = get_regcache_arch (regcache); 00266 00267 rec = xcalloc (1, sizeof (struct record_full_entry)); 00268 rec->type = record_full_reg; 00269 rec->u.reg.num = regnum; 00270 rec->u.reg.len = register_size (gdbarch, regnum); 00271 if (rec->u.reg.len > sizeof (rec->u.reg.u.buf)) 00272 rec->u.reg.u.ptr = (gdb_byte *) xmalloc (rec->u.reg.len); 00273 00274 return rec; 00275 } 00276 00277 /* Free a record_full_reg record entry. */ 00278 00279 static inline void 00280 record_full_reg_release (struct record_full_entry *rec) 00281 { 00282 gdb_assert (rec->type == record_full_reg); 00283 if (rec->u.reg.len > sizeof (rec->u.reg.u.buf)) 00284 xfree (rec->u.reg.u.ptr); 00285 xfree (rec); 00286 } 00287 00288 /* Alloc a record_full_mem record entry. */ 00289 00290 static inline struct record_full_entry * 00291 record_full_mem_alloc (CORE_ADDR addr, int len) 00292 { 00293 struct record_full_entry *rec; 00294 00295 rec = xcalloc (1, sizeof (struct record_full_entry)); 00296 rec->type = record_full_mem; 00297 rec->u.mem.addr = addr; 00298 rec->u.mem.len = len; 00299 if (rec->u.mem.len > sizeof (rec->u.mem.u.buf)) 00300 rec->u.mem.u.ptr = (gdb_byte *) xmalloc (len); 00301 00302 return rec; 00303 } 00304 00305 /* Free a record_full_mem record entry. */ 00306 00307 static inline void 00308 record_full_mem_release (struct record_full_entry *rec) 00309 { 00310 gdb_assert (rec->type == record_full_mem); 00311 if (rec->u.mem.len > sizeof (rec->u.mem.u.buf)) 00312 xfree (rec->u.mem.u.ptr); 00313 xfree (rec); 00314 } 00315 00316 /* Alloc a record_full_end record entry. */ 00317 00318 static inline struct record_full_entry * 00319 record_full_end_alloc (void) 00320 { 00321 struct record_full_entry *rec; 00322 00323 rec = xcalloc (1, sizeof (struct record_full_entry)); 00324 rec->type = record_full_end; 00325 00326 return rec; 00327 } 00328 00329 /* Free a record_full_end record entry. */ 00330 00331 static inline void 00332 record_full_end_release (struct record_full_entry *rec) 00333 { 00334 xfree (rec); 00335 } 00336 00337 /* Free one record entry, any type. 00338 Return entry->type, in case caller wants to know. */ 00339 00340 static inline enum record_full_type 00341 record_full_entry_release (struct record_full_entry *rec) 00342 { 00343 enum record_full_type type = rec->type; 00344 00345 switch (type) { 00346 case record_full_reg: 00347 record_full_reg_release (rec); 00348 break; 00349 case record_full_mem: 00350 record_full_mem_release (rec); 00351 break; 00352 case record_full_end: 00353 record_full_end_release (rec); 00354 break; 00355 } 00356 return type; 00357 } 00358 00359 /* Free all record entries in list pointed to by REC. */ 00360 00361 static void 00362 record_full_list_release (struct record_full_entry *rec) 00363 { 00364 if (!rec) 00365 return; 00366 00367 while (rec->next) 00368 rec = rec->next; 00369 00370 while (rec->prev) 00371 { 00372 rec = rec->prev; 00373 record_full_entry_release (rec->next); 00374 } 00375 00376 if (rec == &record_full_first) 00377 { 00378 record_full_insn_num = 0; 00379 record_full_first.next = NULL; 00380 } 00381 else 00382 record_full_entry_release (rec); 00383 } 00384 00385 /* Free all record entries forward of the given list position. */ 00386 00387 static void 00388 record_full_list_release_following (struct record_full_entry *rec) 00389 { 00390 struct record_full_entry *tmp = rec->next; 00391 00392 rec->next = NULL; 00393 while (tmp) 00394 { 00395 rec = tmp->next; 00396 if (record_full_entry_release (tmp) == record_full_end) 00397 { 00398 record_full_insn_num--; 00399 record_full_insn_count--; 00400 } 00401 tmp = rec; 00402 } 00403 } 00404 00405 /* Delete the first instruction from the beginning of the log, to make 00406 room for adding a new instruction at the end of the log. 00407 00408 Note -- this function does not modify record_full_insn_num. */ 00409 00410 static void 00411 record_full_list_release_first (void) 00412 { 00413 struct record_full_entry *tmp; 00414 00415 if (!record_full_first.next) 00416 return; 00417 00418 /* Loop until a record_full_end. */ 00419 while (1) 00420 { 00421 /* Cut record_full_first.next out of the linked list. */ 00422 tmp = record_full_first.next; 00423 record_full_first.next = tmp->next; 00424 tmp->next->prev = &record_full_first; 00425 00426 /* tmp is now isolated, and can be deleted. */ 00427 if (record_full_entry_release (tmp) == record_full_end) 00428 break; /* End loop at first record_full_end. */ 00429 00430 if (!record_full_first.next) 00431 { 00432 gdb_assert (record_full_insn_num == 1); 00433 break; /* End loop when list is empty. */ 00434 } 00435 } 00436 } 00437 00438 /* Add a struct record_full_entry to record_full_arch_list. */ 00439 00440 static void 00441 record_full_arch_list_add (struct record_full_entry *rec) 00442 { 00443 if (record_debug > 1) 00444 fprintf_unfiltered (gdb_stdlog, 00445 "Process record: record_full_arch_list_add %s.\n", 00446 host_address_to_string (rec)); 00447 00448 if (record_full_arch_list_tail) 00449 { 00450 record_full_arch_list_tail->next = rec; 00451 rec->prev = record_full_arch_list_tail; 00452 record_full_arch_list_tail = rec; 00453 } 00454 else 00455 { 00456 record_full_arch_list_head = rec; 00457 record_full_arch_list_tail = rec; 00458 } 00459 } 00460 00461 /* Return the value storage location of a record entry. */ 00462 static inline gdb_byte * 00463 record_full_get_loc (struct record_full_entry *rec) 00464 { 00465 switch (rec->type) { 00466 case record_full_mem: 00467 if (rec->u.mem.len > sizeof (rec->u.mem.u.buf)) 00468 return rec->u.mem.u.ptr; 00469 else 00470 return rec->u.mem.u.buf; 00471 case record_full_reg: 00472 if (rec->u.reg.len > sizeof (rec->u.reg.u.buf)) 00473 return rec->u.reg.u.ptr; 00474 else 00475 return rec->u.reg.u.buf; 00476 case record_full_end: 00477 default: 00478 gdb_assert_not_reached ("unexpected record_full_entry type"); 00479 return NULL; 00480 } 00481 } 00482 00483 /* Record the value of a register NUM to record_full_arch_list. */ 00484 00485 int 00486 record_full_arch_list_add_reg (struct regcache *regcache, int regnum) 00487 { 00488 struct record_full_entry *rec; 00489 00490 if (record_debug > 1) 00491 fprintf_unfiltered (gdb_stdlog, 00492 "Process record: add register num = %d to " 00493 "record list.\n", 00494 regnum); 00495 00496 rec = record_full_reg_alloc (regcache, regnum); 00497 00498 regcache_raw_read (regcache, regnum, record_full_get_loc (rec)); 00499 00500 record_full_arch_list_add (rec); 00501 00502 return 0; 00503 } 00504 00505 /* Record the value of a region of memory whose address is ADDR and 00506 length is LEN to record_full_arch_list. */ 00507 00508 int 00509 record_full_arch_list_add_mem (CORE_ADDR addr, int len) 00510 { 00511 struct record_full_entry *rec; 00512 00513 if (record_debug > 1) 00514 fprintf_unfiltered (gdb_stdlog, 00515 "Process record: add mem addr = %s len = %d to " 00516 "record list.\n", 00517 paddress (target_gdbarch (), addr), len); 00518 00519 if (!addr) /* FIXME: Why? Some arch must permit it... */ 00520 return 0; 00521 00522 rec = record_full_mem_alloc (addr, len); 00523 00524 if (record_read_memory (target_gdbarch (), addr, 00525 record_full_get_loc (rec), len)) 00526 { 00527 record_full_mem_release (rec); 00528 return -1; 00529 } 00530 00531 record_full_arch_list_add (rec); 00532 00533 return 0; 00534 } 00535 00536 /* Add a record_full_end type struct record_full_entry to 00537 record_full_arch_list. */ 00538 00539 int 00540 record_full_arch_list_add_end (void) 00541 { 00542 struct record_full_entry *rec; 00543 00544 if (record_debug > 1) 00545 fprintf_unfiltered (gdb_stdlog, 00546 "Process record: add end to arch list.\n"); 00547 00548 rec = record_full_end_alloc (); 00549 rec->u.end.sigval = GDB_SIGNAL_0; 00550 rec->u.end.insn_num = ++record_full_insn_count; 00551 00552 record_full_arch_list_add (rec); 00553 00554 return 0; 00555 } 00556 00557 static void 00558 record_full_check_insn_num (int set_terminal) 00559 { 00560 if (record_full_insn_num == record_full_insn_max_num) 00561 { 00562 /* Ask user what to do. */ 00563 if (record_full_stop_at_limit) 00564 { 00565 int q; 00566 00567 if (set_terminal) 00568 target_terminal_ours (); 00569 q = yquery (_("Do you want to auto delete previous execution " 00570 "log entries when record/replay buffer becomes " 00571 "full (record full stop-at-limit)?")); 00572 if (set_terminal) 00573 target_terminal_inferior (); 00574 if (q) 00575 record_full_stop_at_limit = 0; 00576 else 00577 error (_("Process record: stopped by user.")); 00578 } 00579 } 00580 } 00581 00582 static void 00583 record_full_arch_list_cleanups (void *ignore) 00584 { 00585 record_full_list_release (record_full_arch_list_tail); 00586 } 00587 00588 /* Before inferior step (when GDB record the running message, inferior 00589 only can step), GDB will call this function to record the values to 00590 record_full_list. This function will call gdbarch_process_record to 00591 record the running message of inferior and set them to 00592 record_full_arch_list, and add it to record_full_list. */ 00593 00594 static int 00595 record_full_message (struct regcache *regcache, enum gdb_signal signal) 00596 { 00597 int ret; 00598 struct gdbarch *gdbarch = get_regcache_arch (regcache); 00599 struct cleanup *old_cleanups 00600 = make_cleanup (record_full_arch_list_cleanups, 0); 00601 00602 record_full_arch_list_head = NULL; 00603 record_full_arch_list_tail = NULL; 00604 00605 /* Check record_full_insn_num. */ 00606 record_full_check_insn_num (1); 00607 00608 /* If gdb sends a signal value to target_resume, 00609 save it in the 'end' field of the previous instruction. 00610 00611 Maybe process record should record what really happened, 00612 rather than what gdb pretends has happened. 00613 00614 So if Linux delivered the signal to the child process during 00615 the record mode, we will record it and deliver it again in 00616 the replay mode. 00617 00618 If user says "ignore this signal" during the record mode, then 00619 it will be ignored again during the replay mode (no matter if 00620 the user says something different, like "deliver this signal" 00621 during the replay mode). 00622 00623 User should understand that nothing he does during the replay 00624 mode will change the behavior of the child. If he tries, 00625 then that is a user error. 00626 00627 But we should still deliver the signal to gdb during the replay, 00628 if we delivered it during the recording. Therefore we should 00629 record the signal during record_full_wait, not 00630 record_full_resume. */ 00631 if (record_full_list != &record_full_first) /* FIXME better way to check */ 00632 { 00633 gdb_assert (record_full_list->type == record_full_end); 00634 record_full_list->u.end.sigval = signal; 00635 } 00636 00637 if (signal == GDB_SIGNAL_0 00638 || !gdbarch_process_record_signal_p (gdbarch)) 00639 ret = gdbarch_process_record (gdbarch, 00640 regcache, 00641 regcache_read_pc (regcache)); 00642 else 00643 ret = gdbarch_process_record_signal (gdbarch, 00644 regcache, 00645 signal); 00646 00647 if (ret > 0) 00648 error (_("Process record: inferior program stopped.")); 00649 if (ret < 0) 00650 error (_("Process record: failed to record execution log.")); 00651 00652 discard_cleanups (old_cleanups); 00653 00654 record_full_list->next = record_full_arch_list_head; 00655 record_full_arch_list_head->prev = record_full_list; 00656 record_full_list = record_full_arch_list_tail; 00657 00658 if (record_full_insn_num == record_full_insn_max_num) 00659 record_full_list_release_first (); 00660 else 00661 record_full_insn_num++; 00662 00663 return 1; 00664 } 00665 00666 struct record_full_message_args { 00667 struct regcache *regcache; 00668 enum gdb_signal signal; 00669 }; 00670 00671 static int 00672 record_full_message_wrapper (void *args) 00673 { 00674 struct record_full_message_args *record_full_args = args; 00675 00676 return record_full_message (record_full_args->regcache, 00677 record_full_args->signal); 00678 } 00679 00680 static int 00681 record_full_message_wrapper_safe (struct regcache *regcache, 00682 enum gdb_signal signal) 00683 { 00684 struct record_full_message_args args; 00685 00686 args.regcache = regcache; 00687 args.signal = signal; 00688 00689 return catch_errors (record_full_message_wrapper, &args, NULL, 00690 RETURN_MASK_ALL); 00691 } 00692 00693 /* Set to 1 if record_full_store_registers and record_full_xfer_partial 00694 doesn't need record. */ 00695 00696 static int record_full_gdb_operation_disable = 0; 00697 00698 struct cleanup * 00699 record_full_gdb_operation_disable_set (void) 00700 { 00701 struct cleanup *old_cleanups = NULL; 00702 00703 old_cleanups = 00704 make_cleanup_restore_integer (&record_full_gdb_operation_disable); 00705 record_full_gdb_operation_disable = 1; 00706 00707 return old_cleanups; 00708 } 00709 00710 /* Flag set to TRUE for target_stopped_by_watchpoint. */ 00711 static int record_full_hw_watchpoint = 0; 00712 00713 /* Execute one instruction from the record log. Each instruction in 00714 the log will be represented by an arbitrary sequence of register 00715 entries and memory entries, followed by an 'end' entry. */ 00716 00717 static inline void 00718 record_full_exec_insn (struct regcache *regcache, 00719 struct gdbarch *gdbarch, 00720 struct record_full_entry *entry) 00721 { 00722 switch (entry->type) 00723 { 00724 case record_full_reg: /* reg */ 00725 { 00726 gdb_byte reg[MAX_REGISTER_SIZE]; 00727 00728 if (record_debug > 1) 00729 fprintf_unfiltered (gdb_stdlog, 00730 "Process record: record_full_reg %s to " 00731 "inferior num = %d.\n", 00732 host_address_to_string (entry), 00733 entry->u.reg.num); 00734 00735 regcache_cooked_read (regcache, entry->u.reg.num, reg); 00736 regcache_cooked_write (regcache, entry->u.reg.num, 00737 record_full_get_loc (entry)); 00738 memcpy (record_full_get_loc (entry), reg, entry->u.reg.len); 00739 } 00740 break; 00741 00742 case record_full_mem: /* mem */ 00743 { 00744 /* Nothing to do if the entry is flagged not_accessible. */ 00745 if (!entry->u.mem.mem_entry_not_accessible) 00746 { 00747 gdb_byte *mem = alloca (entry->u.mem.len); 00748 00749 if (record_debug > 1) 00750 fprintf_unfiltered (gdb_stdlog, 00751 "Process record: record_full_mem %s to " 00752 "inferior addr = %s len = %d.\n", 00753 host_address_to_string (entry), 00754 paddress (gdbarch, entry->u.mem.addr), 00755 entry->u.mem.len); 00756 00757 if (record_read_memory (gdbarch, 00758 entry->u.mem.addr, mem, entry->u.mem.len)) 00759 entry->u.mem.mem_entry_not_accessible = 1; 00760 else 00761 { 00762 if (target_write_memory (entry->u.mem.addr, 00763 record_full_get_loc (entry), 00764 entry->u.mem.len)) 00765 { 00766 entry->u.mem.mem_entry_not_accessible = 1; 00767 if (record_debug) 00768 warning (_("Process record: error writing memory at " 00769 "addr = %s len = %d."), 00770 paddress (gdbarch, entry->u.mem.addr), 00771 entry->u.mem.len); 00772 } 00773 else 00774 { 00775 memcpy (record_full_get_loc (entry), mem, 00776 entry->u.mem.len); 00777 00778 /* We've changed memory --- check if a hardware 00779 watchpoint should trap. Note that this 00780 presently assumes the target beneath supports 00781 continuable watchpoints. On non-continuable 00782 watchpoints target, we'll want to check this 00783 _before_ actually doing the memory change, and 00784 not doing the change at all if the watchpoint 00785 traps. */ 00786 if (hardware_watchpoint_inserted_in_range 00787 (get_regcache_aspace (regcache), 00788 entry->u.mem.addr, entry->u.mem.len)) 00789 record_full_hw_watchpoint = 1; 00790 } 00791 } 00792 } 00793 } 00794 break; 00795 } 00796 } 00797 00798 static struct target_ops *tmp_to_resume_ops; 00799 static void (*tmp_to_resume) (struct target_ops *, ptid_t, int, 00800 enum gdb_signal); 00801 static struct target_ops *tmp_to_wait_ops; 00802 static ptid_t (*tmp_to_wait) (struct target_ops *, ptid_t, 00803 struct target_waitstatus *, 00804 int); 00805 static struct target_ops *tmp_to_store_registers_ops; 00806 static void (*tmp_to_store_registers) (struct target_ops *, 00807 struct regcache *, 00808 int regno); 00809 static struct target_ops *tmp_to_xfer_partial_ops; 00810 static LONGEST (*tmp_to_xfer_partial) (struct target_ops *ops, 00811 enum target_object object, 00812 const char *annex, 00813 gdb_byte *readbuf, 00814 const gdb_byte *writebuf, 00815 ULONGEST offset, 00816 LONGEST len); 00817 static int (*tmp_to_insert_breakpoint) (struct gdbarch *, 00818 struct bp_target_info *); 00819 static int (*tmp_to_remove_breakpoint) (struct gdbarch *, 00820 struct bp_target_info *); 00821 static int (*tmp_to_stopped_by_watchpoint) (void); 00822 static int (*tmp_to_stopped_data_address) (struct target_ops *, CORE_ADDR *); 00823 static int (*tmp_to_stopped_data_address) (struct target_ops *, CORE_ADDR *); 00824 static void (*tmp_to_async) (void (*) (enum inferior_event_type, void *), void *); 00825 00826 static void record_full_restore (void); 00827 00828 /* Asynchronous signal handle registered as event loop source for when 00829 we have pending events ready to be passed to the core. */ 00830 00831 static struct async_event_handler *record_full_async_inferior_event_token; 00832 00833 static void 00834 record_full_async_inferior_event_handler (gdb_client_data data) 00835 { 00836 inferior_event_handler (INF_REG_EVENT, NULL); 00837 } 00838 00839 /* Open the process record target. */ 00840 00841 static void 00842 record_full_core_open_1 (char *name, int from_tty) 00843 { 00844 struct regcache *regcache = get_current_regcache (); 00845 int regnum = gdbarch_num_regs (get_regcache_arch (regcache)); 00846 int i; 00847 00848 /* Get record_full_core_regbuf. */ 00849 target_fetch_registers (regcache, -1); 00850 record_full_core_regbuf = xmalloc (MAX_REGISTER_SIZE * regnum); 00851 for (i = 0; i < regnum; i ++) 00852 regcache_raw_collect (regcache, i, 00853 record_full_core_regbuf + MAX_REGISTER_SIZE * i); 00854 00855 /* Get record_full_core_start and record_full_core_end. */ 00856 if (build_section_table (core_bfd, &record_full_core_start, 00857 &record_full_core_end)) 00858 { 00859 xfree (record_full_core_regbuf); 00860 record_full_core_regbuf = NULL; 00861 error (_("\"%s\": Can't find sections: %s"), 00862 bfd_get_filename (core_bfd), bfd_errmsg (bfd_get_error ())); 00863 } 00864 00865 push_target (&record_full_core_ops); 00866 record_full_restore (); 00867 } 00868 00869 /* "to_open" target method for 'live' processes. */ 00870 00871 static void 00872 record_full_open_1 (char *name, int from_tty) 00873 { 00874 if (record_debug) 00875 fprintf_unfiltered (gdb_stdlog, "Process record: record_full_open\n"); 00876 00877 /* check exec */ 00878 if (!target_has_execution) 00879 error (_("Process record: the program is not being run.")); 00880 if (non_stop) 00881 error (_("Process record target can't debug inferior in non-stop mode " 00882 "(non-stop).")); 00883 00884 if (!gdbarch_process_record_p (target_gdbarch ())) 00885 error (_("Process record: the current architecture doesn't support " 00886 "record function.")); 00887 00888 if (!tmp_to_resume) 00889 error (_("Could not find 'to_resume' method on the target stack.")); 00890 if (!tmp_to_wait) 00891 error (_("Could not find 'to_wait' method on the target stack.")); 00892 if (!tmp_to_store_registers) 00893 error (_("Could not find 'to_store_registers' " 00894 "method on the target stack.")); 00895 if (!tmp_to_insert_breakpoint) 00896 error (_("Could not find 'to_insert_breakpoint' " 00897 "method on the target stack.")); 00898 if (!tmp_to_remove_breakpoint) 00899 error (_("Could not find 'to_remove_breakpoint' " 00900 "method on the target stack.")); 00901 if (!tmp_to_stopped_by_watchpoint) 00902 error (_("Could not find 'to_stopped_by_watchpoint' " 00903 "method on the target stack.")); 00904 if (!tmp_to_stopped_data_address) 00905 error (_("Could not find 'to_stopped_data_address' " 00906 "method on the target stack.")); 00907 00908 push_target (&record_full_ops); 00909 } 00910 00911 static void record_full_init_record_breakpoints (void); 00912 00913 /* "to_open" target method. Open the process record target. */ 00914 00915 static void 00916 record_full_open (char *name, int from_tty) 00917 { 00918 struct target_ops *t; 00919 00920 if (record_debug) 00921 fprintf_unfiltered (gdb_stdlog, "Process record: record_full_open\n"); 00922 00923 /* Check if record target is already running. */ 00924 if (current_target.to_stratum == record_stratum) 00925 error (_("Process record target already running. Use \"record stop\" to " 00926 "stop record target first.")); 00927 00928 /* Reset the tmp beneath pointers. */ 00929 tmp_to_resume_ops = NULL; 00930 tmp_to_resume = NULL; 00931 tmp_to_wait_ops = NULL; 00932 tmp_to_wait = NULL; 00933 tmp_to_store_registers_ops = NULL; 00934 tmp_to_store_registers = NULL; 00935 tmp_to_xfer_partial_ops = NULL; 00936 tmp_to_xfer_partial = NULL; 00937 tmp_to_insert_breakpoint = NULL; 00938 tmp_to_remove_breakpoint = NULL; 00939 tmp_to_stopped_by_watchpoint = NULL; 00940 tmp_to_stopped_data_address = NULL; 00941 tmp_to_async = NULL; 00942 00943 /* Set the beneath function pointers. */ 00944 for (t = current_target.beneath; t != NULL; t = t->beneath) 00945 { 00946 if (!tmp_to_resume) 00947 { 00948 tmp_to_resume = t->to_resume; 00949 tmp_to_resume_ops = t; 00950 } 00951 if (!tmp_to_wait) 00952 { 00953 tmp_to_wait = t->to_wait; 00954 tmp_to_wait_ops = t; 00955 } 00956 if (!tmp_to_store_registers) 00957 { 00958 tmp_to_store_registers = t->to_store_registers; 00959 tmp_to_store_registers_ops = t; 00960 } 00961 if (!tmp_to_xfer_partial) 00962 { 00963 tmp_to_xfer_partial = t->to_xfer_partial; 00964 tmp_to_xfer_partial_ops = t; 00965 } 00966 if (!tmp_to_insert_breakpoint) 00967 tmp_to_insert_breakpoint = t->to_insert_breakpoint; 00968 if (!tmp_to_remove_breakpoint) 00969 tmp_to_remove_breakpoint = t->to_remove_breakpoint; 00970 if (!tmp_to_stopped_by_watchpoint) 00971 tmp_to_stopped_by_watchpoint = t->to_stopped_by_watchpoint; 00972 if (!tmp_to_stopped_data_address) 00973 tmp_to_stopped_data_address = t->to_stopped_data_address; 00974 if (!tmp_to_async) 00975 tmp_to_async = t->to_async; 00976 } 00977 if (!tmp_to_xfer_partial) 00978 error (_("Could not find 'to_xfer_partial' method on the target stack.")); 00979 00980 /* Reset */ 00981 record_full_insn_num = 0; 00982 record_full_insn_count = 0; 00983 record_full_list = &record_full_first; 00984 record_full_list->next = NULL; 00985 00986 /* Set the tmp beneath pointers to beneath pointers. */ 00987 record_full_beneath_to_resume_ops = tmp_to_resume_ops; 00988 record_full_beneath_to_resume = tmp_to_resume; 00989 record_full_beneath_to_wait_ops = tmp_to_wait_ops; 00990 record_full_beneath_to_wait = tmp_to_wait; 00991 record_full_beneath_to_store_registers_ops = tmp_to_store_registers_ops; 00992 record_full_beneath_to_store_registers = tmp_to_store_registers; 00993 record_full_beneath_to_xfer_partial_ops = tmp_to_xfer_partial_ops; 00994 record_full_beneath_to_xfer_partial = tmp_to_xfer_partial; 00995 record_full_beneath_to_insert_breakpoint = tmp_to_insert_breakpoint; 00996 record_full_beneath_to_remove_breakpoint = tmp_to_remove_breakpoint; 00997 record_full_beneath_to_stopped_by_watchpoint = tmp_to_stopped_by_watchpoint; 00998 record_full_beneath_to_stopped_data_address = tmp_to_stopped_data_address; 00999 record_full_beneath_to_async = tmp_to_async; 01000 01001 if (core_bfd) 01002 record_full_core_open_1 (name, from_tty); 01003 else 01004 record_full_open_1 (name, from_tty); 01005 01006 /* Register extra event sources in the event loop. */ 01007 record_full_async_inferior_event_token 01008 = create_async_event_handler (record_full_async_inferior_event_handler, 01009 NULL); 01010 01011 record_full_init_record_breakpoints (); 01012 01013 observer_notify_record_changed (current_inferior (), 1); 01014 } 01015 01016 /* "to_close" target method. Close the process record target. */ 01017 01018 static void 01019 record_full_close (void) 01020 { 01021 struct record_full_core_buf_entry *entry; 01022 01023 if (record_debug) 01024 fprintf_unfiltered (gdb_stdlog, "Process record: record_full_close\n"); 01025 01026 record_full_list_release (record_full_list); 01027 01028 /* Release record_full_core_regbuf. */ 01029 if (record_full_core_regbuf) 01030 { 01031 xfree (record_full_core_regbuf); 01032 record_full_core_regbuf = NULL; 01033 } 01034 01035 /* Release record_full_core_buf_list. */ 01036 if (record_full_core_buf_list) 01037 { 01038 for (entry = record_full_core_buf_list->prev; entry; 01039 entry = entry->prev) 01040 { 01041 xfree (record_full_core_buf_list); 01042 record_full_core_buf_list = entry; 01043 } 01044 record_full_core_buf_list = NULL; 01045 } 01046 01047 if (record_full_async_inferior_event_token) 01048 delete_async_event_handler (&record_full_async_inferior_event_token); 01049 } 01050 01051 static int record_full_resume_step = 0; 01052 01053 /* True if we've been resumed, and so each record_full_wait call should 01054 advance execution. If this is false, record_full_wait will return a 01055 TARGET_WAITKIND_IGNORE. */ 01056 static int record_full_resumed = 0; 01057 01058 /* The execution direction of the last resume we got. This is 01059 necessary for async mode. Vis (order is not strictly accurate): 01060 01061 1. user has the global execution direction set to forward 01062 2. user does a reverse-step command 01063 3. record_full_resume is called with global execution direction 01064 temporarily switched to reverse 01065 4. GDB's execution direction is reverted back to forward 01066 5. target record notifies event loop there's an event to handle 01067 6. infrun asks the target which direction was it going, and switches 01068 the global execution direction accordingly (to reverse) 01069 7. infrun polls an event out of the record target, and handles it 01070 8. GDB goes back to the event loop, and goto #4. 01071 */ 01072 static enum exec_direction_kind record_full_execution_dir = EXEC_FORWARD; 01073 01074 /* "to_resume" target method. Resume the process record target. */ 01075 01076 static void 01077 record_full_resume (struct target_ops *ops, ptid_t ptid, int step, 01078 enum gdb_signal signal) 01079 { 01080 record_full_resume_step = step; 01081 record_full_resumed = 1; 01082 record_full_execution_dir = execution_direction; 01083 01084 if (!RECORD_FULL_IS_REPLAY) 01085 { 01086 struct gdbarch *gdbarch = target_thread_architecture (ptid); 01087 01088 record_full_message (get_current_regcache (), signal); 01089 01090 if (!step) 01091 { 01092 /* This is not hard single step. */ 01093 if (!gdbarch_software_single_step_p (gdbarch)) 01094 { 01095 /* This is a normal continue. */ 01096 step = 1; 01097 } 01098 else 01099 { 01100 /* This arch support soft sigle step. */ 01101 if (single_step_breakpoints_inserted ()) 01102 { 01103 /* This is a soft single step. */ 01104 record_full_resume_step = 1; 01105 } 01106 else 01107 { 01108 /* This is a continue. 01109 Try to insert a soft single step breakpoint. */ 01110 if (!gdbarch_software_single_step (gdbarch, 01111 get_current_frame ())) 01112 { 01113 /* This system don't want use soft single step. 01114 Use hard sigle step. */ 01115 step = 1; 01116 } 01117 } 01118 } 01119 } 01120 01121 /* Make sure the target beneath reports all signals. */ 01122 target_pass_signals (0, NULL); 01123 01124 record_full_beneath_to_resume (record_full_beneath_to_resume_ops, 01125 ptid, step, signal); 01126 } 01127 01128 /* We are about to start executing the inferior (or simulate it), 01129 let's register it with the event loop. */ 01130 if (target_can_async_p ()) 01131 { 01132 target_async (inferior_event_handler, 0); 01133 /* Notify the event loop there's an event to wait for. We do 01134 most of the work in record_full_wait. */ 01135 mark_async_event_handler (record_full_async_inferior_event_token); 01136 } 01137 } 01138 01139 static int record_full_get_sig = 0; 01140 01141 /* SIGINT signal handler, registered by "to_wait" method. */ 01142 01143 static void 01144 record_full_sig_handler (int signo) 01145 { 01146 if (record_debug) 01147 fprintf_unfiltered (gdb_stdlog, "Process record: get a signal\n"); 01148 01149 /* It will break the running inferior in replay mode. */ 01150 record_full_resume_step = 1; 01151 01152 /* It will let record_full_wait set inferior status to get the signal 01153 SIGINT. */ 01154 record_full_get_sig = 1; 01155 } 01156 01157 static void 01158 record_full_wait_cleanups (void *ignore) 01159 { 01160 if (execution_direction == EXEC_REVERSE) 01161 { 01162 if (record_full_list->next) 01163 record_full_list = record_full_list->next; 01164 } 01165 else 01166 record_full_list = record_full_list->prev; 01167 } 01168 01169 /* "to_wait" target method for process record target. 01170 01171 In record mode, the target is always run in singlestep mode 01172 (even when gdb says to continue). The to_wait method intercepts 01173 the stop events and determines which ones are to be passed on to 01174 gdb. Most stop events are just singlestep events that gdb is not 01175 to know about, so the to_wait method just records them and keeps 01176 singlestepping. 01177 01178 In replay mode, this function emulates the recorded execution log, 01179 one instruction at a time (forward or backward), and determines 01180 where to stop. */ 01181 01182 static ptid_t 01183 record_full_wait_1 (struct target_ops *ops, 01184 ptid_t ptid, struct target_waitstatus *status, 01185 int options) 01186 { 01187 struct cleanup *set_cleanups = record_full_gdb_operation_disable_set (); 01188 01189 if (record_debug) 01190 fprintf_unfiltered (gdb_stdlog, 01191 "Process record: record_full_wait " 01192 "record_full_resume_step = %d, " 01193 "record_full_resumed = %d, direction=%s\n", 01194 record_full_resume_step, record_full_resumed, 01195 record_full_execution_dir == EXEC_FORWARD 01196 ? "forward" : "reverse"); 01197 01198 if (!record_full_resumed) 01199 { 01200 gdb_assert ((options & TARGET_WNOHANG) != 0); 01201 01202 /* No interesting event. */ 01203 status->kind = TARGET_WAITKIND_IGNORE; 01204 return minus_one_ptid; 01205 } 01206 01207 record_full_get_sig = 0; 01208 signal (SIGINT, record_full_sig_handler); 01209 01210 if (!RECORD_FULL_IS_REPLAY && ops != &record_full_core_ops) 01211 { 01212 if (record_full_resume_step) 01213 { 01214 /* This is a single step. */ 01215 return record_full_beneath_to_wait (record_full_beneath_to_wait_ops, 01216 ptid, status, options); 01217 } 01218 else 01219 { 01220 /* This is not a single step. */ 01221 ptid_t ret; 01222 CORE_ADDR tmp_pc; 01223 struct gdbarch *gdbarch = target_thread_architecture (inferior_ptid); 01224 01225 while (1) 01226 { 01227 ret = record_full_beneath_to_wait 01228 (record_full_beneath_to_wait_ops, ptid, status, options); 01229 if (status->kind == TARGET_WAITKIND_IGNORE) 01230 { 01231 if (record_debug) 01232 fprintf_unfiltered (gdb_stdlog, 01233 "Process record: record_full_wait " 01234 "target beneath not done yet\n"); 01235 return ret; 01236 } 01237 01238 if (single_step_breakpoints_inserted ()) 01239 remove_single_step_breakpoints (); 01240 01241 if (record_full_resume_step) 01242 return ret; 01243 01244 /* Is this a SIGTRAP? */ 01245 if (status->kind == TARGET_WAITKIND_STOPPED 01246 && status->value.sig == GDB_SIGNAL_TRAP) 01247 { 01248 struct regcache *regcache; 01249 struct address_space *aspace; 01250 01251 /* Yes -- this is likely our single-step finishing, 01252 but check if there's any reason the core would be 01253 interested in the event. */ 01254 01255 registers_changed (); 01256 regcache = get_current_regcache (); 01257 tmp_pc = regcache_read_pc (regcache); 01258 aspace = get_regcache_aspace (regcache); 01259 01260 if (target_stopped_by_watchpoint ()) 01261 { 01262 /* Always interested in watchpoints. */ 01263 } 01264 else if (breakpoint_inserted_here_p (aspace, tmp_pc)) 01265 { 01266 /* There is a breakpoint here. Let the core 01267 handle it. */ 01268 if (software_breakpoint_inserted_here_p (aspace, tmp_pc)) 01269 { 01270 struct gdbarch *gdbarch 01271 = get_regcache_arch (regcache); 01272 CORE_ADDR decr_pc_after_break 01273 = gdbarch_decr_pc_after_break (gdbarch); 01274 if (decr_pc_after_break) 01275 regcache_write_pc (regcache, 01276 tmp_pc + decr_pc_after_break); 01277 } 01278 } 01279 else 01280 { 01281 /* This is a single-step trap. Record the 01282 insn and issue another step. 01283 FIXME: this part can be a random SIGTRAP too. 01284 But GDB cannot handle it. */ 01285 int step = 1; 01286 01287 if (!record_full_message_wrapper_safe (regcache, 01288 GDB_SIGNAL_0)) 01289 { 01290 status->kind = TARGET_WAITKIND_STOPPED; 01291 status->value.sig = GDB_SIGNAL_0; 01292 break; 01293 } 01294 01295 if (gdbarch_software_single_step_p (gdbarch)) 01296 { 01297 /* Try to insert the software single step breakpoint. 01298 If insert success, set step to 0. */ 01299 set_executing (inferior_ptid, 0); 01300 reinit_frame_cache (); 01301 if (gdbarch_software_single_step (gdbarch, 01302 get_current_frame ())) 01303 step = 0; 01304 set_executing (inferior_ptid, 1); 01305 } 01306 01307 if (record_debug) 01308 fprintf_unfiltered (gdb_stdlog, 01309 "Process record: record_full_wait " 01310 "issuing one more step in the " 01311 "target beneath\n"); 01312 record_full_beneath_to_resume 01313 (record_full_beneath_to_resume_ops, ptid, step, 01314 GDB_SIGNAL_0); 01315 continue; 01316 } 01317 } 01318 01319 /* The inferior is broken by a breakpoint or a signal. */ 01320 break; 01321 } 01322 01323 return ret; 01324 } 01325 } 01326 else 01327 { 01328 struct regcache *regcache = get_current_regcache (); 01329 struct gdbarch *gdbarch = get_regcache_arch (regcache); 01330 struct address_space *aspace = get_regcache_aspace (regcache); 01331 int continue_flag = 1; 01332 int first_record_full_end = 1; 01333 struct cleanup *old_cleanups 01334 = make_cleanup (record_full_wait_cleanups, 0); 01335 CORE_ADDR tmp_pc; 01336 01337 record_full_hw_watchpoint = 0; 01338 status->kind = TARGET_WAITKIND_STOPPED; 01339 01340 /* Check breakpoint when forward execute. */ 01341 if (execution_direction == EXEC_FORWARD) 01342 { 01343 tmp_pc = regcache_read_pc (regcache); 01344 if (breakpoint_inserted_here_p (aspace, tmp_pc)) 01345 { 01346 int decr_pc_after_break = gdbarch_decr_pc_after_break (gdbarch); 01347 01348 if (record_debug) 01349 fprintf_unfiltered (gdb_stdlog, 01350 "Process record: break at %s.\n", 01351 paddress (gdbarch, tmp_pc)); 01352 01353 if (decr_pc_after_break 01354 && !record_full_resume_step 01355 && software_breakpoint_inserted_here_p (aspace, tmp_pc)) 01356 regcache_write_pc (regcache, 01357 tmp_pc + decr_pc_after_break); 01358 goto replay_out; 01359 } 01360 } 01361 01362 /* If GDB is in terminal_inferior mode, it will not get the signal. 01363 And in GDB replay mode, GDB doesn't need to be in terminal_inferior 01364 mode, because inferior will not executed. 01365 Then set it to terminal_ours to make GDB get the signal. */ 01366 target_terminal_ours (); 01367 01368 /* In EXEC_FORWARD mode, record_full_list points to the tail of prev 01369 instruction. */ 01370 if (execution_direction == EXEC_FORWARD && record_full_list->next) 01371 record_full_list = record_full_list->next; 01372 01373 /* Loop over the record_full_list, looking for the next place to 01374 stop. */ 01375 do 01376 { 01377 /* Check for beginning and end of log. */ 01378 if (execution_direction == EXEC_REVERSE 01379 && record_full_list == &record_full_first) 01380 { 01381 /* Hit beginning of record log in reverse. */ 01382 status->kind = TARGET_WAITKIND_NO_HISTORY; 01383 break; 01384 } 01385 if (execution_direction != EXEC_REVERSE && !record_full_list->next) 01386 { 01387 /* Hit end of record log going forward. */ 01388 status->kind = TARGET_WAITKIND_NO_HISTORY; 01389 break; 01390 } 01391 01392 record_full_exec_insn (regcache, gdbarch, record_full_list); 01393 01394 if (record_full_list->type == record_full_end) 01395 { 01396 if (record_debug > 1) 01397 fprintf_unfiltered (gdb_stdlog, 01398 "Process record: record_full_end %s to " 01399 "inferior.\n", 01400 host_address_to_string (record_full_list)); 01401 01402 if (first_record_full_end && execution_direction == EXEC_REVERSE) 01403 { 01404 /* When reverse excute, the first record_full_end is the 01405 part of current instruction. */ 01406 first_record_full_end = 0; 01407 } 01408 else 01409 { 01410 /* In EXEC_REVERSE mode, this is the record_full_end of prev 01411 instruction. 01412 In EXEC_FORWARD mode, this is the record_full_end of 01413 current instruction. */ 01414 /* step */ 01415 if (record_full_resume_step) 01416 { 01417 if (record_debug > 1) 01418 fprintf_unfiltered (gdb_stdlog, 01419 "Process record: step.\n"); 01420 continue_flag = 0; 01421 } 01422 01423 /* check breakpoint */ 01424 tmp_pc = regcache_read_pc (regcache); 01425 if (breakpoint_inserted_here_p (aspace, tmp_pc)) 01426 { 01427 int decr_pc_after_break 01428 = gdbarch_decr_pc_after_break (gdbarch); 01429 01430 if (record_debug) 01431 fprintf_unfiltered (gdb_stdlog, 01432 "Process record: break " 01433 "at %s.\n", 01434 paddress (gdbarch, tmp_pc)); 01435 if (decr_pc_after_break 01436 && execution_direction == EXEC_FORWARD 01437 && !record_full_resume_step 01438 && software_breakpoint_inserted_here_p (aspace, 01439 tmp_pc)) 01440 regcache_write_pc (regcache, 01441 tmp_pc + decr_pc_after_break); 01442 continue_flag = 0; 01443 } 01444 01445 if (record_full_hw_watchpoint) 01446 { 01447 if (record_debug) 01448 fprintf_unfiltered (gdb_stdlog, 01449 "Process record: hit hw " 01450 "watchpoint.\n"); 01451 continue_flag = 0; 01452 } 01453 /* Check target signal */ 01454 if (record_full_list->u.end.sigval != GDB_SIGNAL_0) 01455 /* FIXME: better way to check */ 01456 continue_flag = 0; 01457 } 01458 } 01459 01460 if (continue_flag) 01461 { 01462 if (execution_direction == EXEC_REVERSE) 01463 { 01464 if (record_full_list->prev) 01465 record_full_list = record_full_list->prev; 01466 } 01467 else 01468 { 01469 if (record_full_list->next) 01470 record_full_list = record_full_list->next; 01471 } 01472 } 01473 } 01474 while (continue_flag); 01475 01476 replay_out: 01477 if (record_full_get_sig) 01478 status->value.sig = GDB_SIGNAL_INT; 01479 else if (record_full_list->u.end.sigval != GDB_SIGNAL_0) 01480 /* FIXME: better way to check */ 01481 status->value.sig = record_full_list->u.end.sigval; 01482 else 01483 status->value.sig = GDB_SIGNAL_TRAP; 01484 01485 discard_cleanups (old_cleanups); 01486 } 01487 01488 signal (SIGINT, handle_sigint); 01489 01490 do_cleanups (set_cleanups); 01491 return inferior_ptid; 01492 } 01493 01494 static ptid_t 01495 record_full_wait (struct target_ops *ops, 01496 ptid_t ptid, struct target_waitstatus *status, 01497 int options) 01498 { 01499 ptid_t return_ptid; 01500 01501 return_ptid = record_full_wait_1 (ops, ptid, status, options); 01502 if (status->kind != TARGET_WAITKIND_IGNORE) 01503 { 01504 /* We're reporting a stop. Make sure any spurious 01505 target_wait(WNOHANG) doesn't advance the target until the 01506 core wants us resumed again. */ 01507 record_full_resumed = 0; 01508 } 01509 return return_ptid; 01510 } 01511 01512 static int 01513 record_full_stopped_by_watchpoint (void) 01514 { 01515 if (RECORD_FULL_IS_REPLAY) 01516 return record_full_hw_watchpoint; 01517 else 01518 return record_full_beneath_to_stopped_by_watchpoint (); 01519 } 01520 01521 static int 01522 record_full_stopped_data_address (struct target_ops *ops, CORE_ADDR *addr_p) 01523 { 01524 if (RECORD_FULL_IS_REPLAY) 01525 return 0; 01526 else 01527 return record_full_beneath_to_stopped_data_address (ops, addr_p); 01528 } 01529 01530 /* Record registers change (by user or by GDB) to list as an instruction. */ 01531 01532 static void 01533 record_full_registers_change (struct regcache *regcache, int regnum) 01534 { 01535 /* Check record_full_insn_num. */ 01536 record_full_check_insn_num (0); 01537 01538 record_full_arch_list_head = NULL; 01539 record_full_arch_list_tail = NULL; 01540 01541 if (regnum < 0) 01542 { 01543 int i; 01544 01545 for (i = 0; i < gdbarch_num_regs (get_regcache_arch (regcache)); i++) 01546 { 01547 if (record_full_arch_list_add_reg (regcache, i)) 01548 { 01549 record_full_list_release (record_full_arch_list_tail); 01550 error (_("Process record: failed to record execution log.")); 01551 } 01552 } 01553 } 01554 else 01555 { 01556 if (record_full_arch_list_add_reg (regcache, regnum)) 01557 { 01558 record_full_list_release (record_full_arch_list_tail); 01559 error (_("Process record: failed to record execution log.")); 01560 } 01561 } 01562 if (record_full_arch_list_add_end ()) 01563 { 01564 record_full_list_release (record_full_arch_list_tail); 01565 error (_("Process record: failed to record execution log.")); 01566 } 01567 record_full_list->next = record_full_arch_list_head; 01568 record_full_arch_list_head->prev = record_full_list; 01569 record_full_list = record_full_arch_list_tail; 01570 01571 if (record_full_insn_num == record_full_insn_max_num) 01572 record_full_list_release_first (); 01573 else 01574 record_full_insn_num++; 01575 } 01576 01577 /* "to_store_registers" method for process record target. */ 01578 01579 static void 01580 record_full_store_registers (struct target_ops *ops, 01581 struct regcache *regcache, 01582 int regno) 01583 { 01584 if (!record_full_gdb_operation_disable) 01585 { 01586 if (RECORD_FULL_IS_REPLAY) 01587 { 01588 int n; 01589 01590 /* Let user choose if he wants to write register or not. */ 01591 if (regno < 0) 01592 n = 01593 query (_("Because GDB is in replay mode, changing the " 01594 "value of a register will make the execution " 01595 "log unusable from this point onward. " 01596 "Change all registers?")); 01597 else 01598 n = 01599 query (_("Because GDB is in replay mode, changing the value " 01600 "of a register will make the execution log unusable " 01601 "from this point onward. Change register %s?"), 01602 gdbarch_register_name (get_regcache_arch (regcache), 01603 regno)); 01604 01605 if (!n) 01606 { 01607 /* Invalidate the value of regcache that was set in function 01608 "regcache_raw_write". */ 01609 if (regno < 0) 01610 { 01611 int i; 01612 01613 for (i = 0; 01614 i < gdbarch_num_regs (get_regcache_arch (regcache)); 01615 i++) 01616 regcache_invalidate (regcache, i); 01617 } 01618 else 01619 regcache_invalidate (regcache, regno); 01620 01621 error (_("Process record canceled the operation.")); 01622 } 01623 01624 /* Destroy the record from here forward. */ 01625 record_full_list_release_following (record_full_list); 01626 } 01627 01628 record_full_registers_change (regcache, regno); 01629 } 01630 record_full_beneath_to_store_registers 01631 (record_full_beneath_to_store_registers_ops, regcache, regno); 01632 } 01633 01634 /* "to_xfer_partial" method. Behavior is conditional on 01635 RECORD_FULL_IS_REPLAY. 01636 In replay mode, we cannot write memory unles we are willing to 01637 invalidate the record/replay log from this point forward. */ 01638 01639 static LONGEST 01640 record_full_xfer_partial (struct target_ops *ops, enum target_object object, 01641 const char *annex, gdb_byte *readbuf, 01642 const gdb_byte *writebuf, ULONGEST offset, 01643 LONGEST len) 01644 { 01645 if (!record_full_gdb_operation_disable 01646 && (object == TARGET_OBJECT_MEMORY 01647 || object == TARGET_OBJECT_RAW_MEMORY) && writebuf) 01648 { 01649 if (RECORD_FULL_IS_REPLAY) 01650 { 01651 /* Let user choose if he wants to write memory or not. */ 01652 if (!query (_("Because GDB is in replay mode, writing to memory " 01653 "will make the execution log unusable from this " 01654 "point onward. Write memory at address %s?"), 01655 paddress (target_gdbarch (), offset))) 01656 error (_("Process record canceled the operation.")); 01657 01658 /* Destroy the record from here forward. */ 01659 record_full_list_release_following (record_full_list); 01660 } 01661 01662 /* Check record_full_insn_num */ 01663 record_full_check_insn_num (0); 01664 01665 /* Record registers change to list as an instruction. */ 01666 record_full_arch_list_head = NULL; 01667 record_full_arch_list_tail = NULL; 01668 if (record_full_arch_list_add_mem (offset, len)) 01669 { 01670 record_full_list_release (record_full_arch_list_tail); 01671 if (record_debug) 01672 fprintf_unfiltered (gdb_stdlog, 01673 "Process record: failed to record " 01674 "execution log."); 01675 return -1; 01676 } 01677 if (record_full_arch_list_add_end ()) 01678 { 01679 record_full_list_release (record_full_arch_list_tail); 01680 if (record_debug) 01681 fprintf_unfiltered (gdb_stdlog, 01682 "Process record: failed to record " 01683 "execution log."); 01684 return -1; 01685 } 01686 record_full_list->next = record_full_arch_list_head; 01687 record_full_arch_list_head->prev = record_full_list; 01688 record_full_list = record_full_arch_list_tail; 01689 01690 if (record_full_insn_num == record_full_insn_max_num) 01691 record_full_list_release_first (); 01692 else 01693 record_full_insn_num++; 01694 } 01695 01696 return record_full_beneath_to_xfer_partial 01697 (record_full_beneath_to_xfer_partial_ops, object, annex, 01698 readbuf, writebuf, offset, len); 01699 } 01700 01701 /* This structure represents a breakpoint inserted while the record 01702 target is active. We use this to know when to install/remove 01703 breakpoints in/from the target beneath. For example, a breakpoint 01704 may be inserted while recording, but removed when not replaying nor 01705 recording. In that case, the breakpoint had not been inserted on 01706 the target beneath, so we should not try to remove it there. */ 01707 01708 struct record_full_breakpoint 01709 { 01710 /* The address and address space the breakpoint was set at. */ 01711 struct address_space *address_space; 01712 CORE_ADDR addr; 01713 01714 /* True when the breakpoint has been also installed in the target 01715 beneath. This will be false for breakpoints set during replay or 01716 when recording. */ 01717 int in_target_beneath; 01718 }; 01719 01720 typedef struct record_full_breakpoint *record_full_breakpoint_p; 01721 DEF_VEC_P(record_full_breakpoint_p); 01722 01723 /* The list of breakpoints inserted while the record target is 01724 active. */ 01725 VEC(record_full_breakpoint_p) *record_full_breakpoints = NULL; 01726 01727 static void 01728 record_full_sync_record_breakpoints (struct bp_location *loc, void *data) 01729 { 01730 if (loc->loc_type != bp_loc_software_breakpoint) 01731 return; 01732 01733 if (loc->inserted) 01734 { 01735 struct record_full_breakpoint *bp = XNEW (struct record_full_breakpoint); 01736 01737 bp->addr = loc->target_info.placed_address; 01738 bp->address_space = loc->target_info.placed_address_space; 01739 01740 bp->in_target_beneath = 1; 01741 01742 VEC_safe_push (record_full_breakpoint_p, record_full_breakpoints, bp); 01743 } 01744 } 01745 01746 /* Sync existing breakpoints to record_full_breakpoints. */ 01747 01748 static void 01749 record_full_init_record_breakpoints (void) 01750 { 01751 VEC_free (record_full_breakpoint_p, record_full_breakpoints); 01752 01753 iterate_over_bp_locations (record_full_sync_record_breakpoints); 01754 } 01755 01756 /* Behavior is conditional on RECORD_FULL_IS_REPLAY. We will not actually 01757 insert or remove breakpoints in the real target when replaying, nor 01758 when recording. */ 01759 01760 static int 01761 record_full_insert_breakpoint (struct gdbarch *gdbarch, 01762 struct bp_target_info *bp_tgt) 01763 { 01764 struct record_full_breakpoint *bp; 01765 int in_target_beneath = 0; 01766 01767 if (!RECORD_FULL_IS_REPLAY) 01768 { 01769 /* When recording, we currently always single-step, so we don't 01770 really need to install regular breakpoints in the inferior. 01771 However, we do have to insert software single-step 01772 breakpoints, in case the target can't hardware step. To keep 01773 things single, we always insert. */ 01774 struct cleanup *old_cleanups; 01775 int ret; 01776 01777 old_cleanups = record_full_gdb_operation_disable_set (); 01778 ret = record_full_beneath_to_insert_breakpoint (gdbarch, bp_tgt); 01779 do_cleanups (old_cleanups); 01780 01781 if (ret != 0) 01782 return ret; 01783 01784 in_target_beneath = 1; 01785 } 01786 01787 bp = XNEW (struct record_full_breakpoint); 01788 bp->addr = bp_tgt->placed_address; 01789 bp->address_space = bp_tgt->placed_address_space; 01790 bp->in_target_beneath = in_target_beneath; 01791 VEC_safe_push (record_full_breakpoint_p, record_full_breakpoints, bp); 01792 return 0; 01793 } 01794 01795 /* "to_remove_breakpoint" method for process record target. */ 01796 01797 static int 01798 record_full_remove_breakpoint (struct gdbarch *gdbarch, 01799 struct bp_target_info *bp_tgt) 01800 { 01801 struct record_full_breakpoint *bp; 01802 int ix; 01803 01804 for (ix = 0; 01805 VEC_iterate (record_full_breakpoint_p, 01806 record_full_breakpoints, ix, bp); 01807 ++ix) 01808 { 01809 if (bp->addr == bp_tgt->placed_address 01810 && bp->address_space == bp_tgt->placed_address_space) 01811 { 01812 if (bp->in_target_beneath) 01813 { 01814 struct cleanup *old_cleanups; 01815 int ret; 01816 01817 old_cleanups = record_full_gdb_operation_disable_set (); 01818 ret = record_full_beneath_to_remove_breakpoint (gdbarch, bp_tgt); 01819 do_cleanups (old_cleanups); 01820 01821 if (ret != 0) 01822 return ret; 01823 } 01824 01825 VEC_unordered_remove (record_full_breakpoint_p, 01826 record_full_breakpoints, ix); 01827 return 0; 01828 } 01829 } 01830 01831 gdb_assert_not_reached ("removing unknown breakpoint"); 01832 } 01833 01834 /* "to_can_execute_reverse" method for process record target. */ 01835 01836 static int 01837 record_full_can_execute_reverse (void) 01838 { 01839 return 1; 01840 } 01841 01842 /* "to_get_bookmark" method for process record and prec over core. */ 01843 01844 static gdb_byte * 01845 record_full_get_bookmark (char *args, int from_tty) 01846 { 01847 char *ret = NULL; 01848 01849 /* Return stringified form of instruction count. */ 01850 if (record_full_list && record_full_list->type == record_full_end) 01851 ret = xstrdup (pulongest (record_full_list->u.end.insn_num)); 01852 01853 if (record_debug) 01854 { 01855 if (ret) 01856 fprintf_unfiltered (gdb_stdlog, 01857 "record_full_get_bookmark returns %s\n", ret); 01858 else 01859 fprintf_unfiltered (gdb_stdlog, 01860 "record_full_get_bookmark returns NULL\n"); 01861 } 01862 return (gdb_byte *) ret; 01863 } 01864 01865 /* "to_goto_bookmark" method for process record and prec over core. */ 01866 01867 static void 01868 record_full_goto_bookmark (gdb_byte *raw_bookmark, int from_tty) 01869 { 01870 char *bookmark = (char *) raw_bookmark; 01871 01872 if (record_debug) 01873 fprintf_unfiltered (gdb_stdlog, 01874 "record_full_goto_bookmark receives %s\n", bookmark); 01875 01876 if (bookmark[0] == '\'' || bookmark[0] == '\"') 01877 { 01878 if (bookmark[strlen (bookmark) - 1] != bookmark[0]) 01879 error (_("Unbalanced quotes: %s"), bookmark); 01880 01881 /* Strip trailing quote. */ 01882 bookmark[strlen (bookmark) - 1] = '\0'; 01883 /* Strip leading quote. */ 01884 bookmark++; 01885 /* Pass along to cmd_record_full_goto. */ 01886 } 01887 01888 cmd_record_goto (bookmark, from_tty); 01889 return; 01890 } 01891 01892 static void 01893 record_full_async (void (*callback) (enum inferior_event_type event_type, 01894 void *context), void *context) 01895 { 01896 /* If we're on top of a line target (e.g., linux-nat, remote), then 01897 set it to async mode as well. Will be NULL if we're sitting on 01898 top of the core target, for "record restore". */ 01899 if (record_full_beneath_to_async != NULL) 01900 record_full_beneath_to_async (callback, context); 01901 } 01902 01903 static int 01904 record_full_can_async_p (void) 01905 { 01906 /* We only enable async when the user specifically asks for it. */ 01907 return target_async_permitted; 01908 } 01909 01910 static int 01911 record_full_is_async_p (void) 01912 { 01913 /* We only enable async when the user specifically asks for it. */ 01914 return target_async_permitted; 01915 } 01916 01917 static enum exec_direction_kind 01918 record_full_execution_direction (void) 01919 { 01920 return record_full_execution_dir; 01921 } 01922 01923 static void 01924 record_full_info (void) 01925 { 01926 struct record_full_entry *p; 01927 01928 if (RECORD_FULL_IS_REPLAY) 01929 printf_filtered (_("Replay mode:\n")); 01930 else 01931 printf_filtered (_("Record mode:\n")); 01932 01933 /* Find entry for first actual instruction in the log. */ 01934 for (p = record_full_first.next; 01935 p != NULL && p->type != record_full_end; 01936 p = p->next) 01937 ; 01938 01939 /* Do we have a log at all? */ 01940 if (p != NULL && p->type == record_full_end) 01941 { 01942 /* Display instruction number for first instruction in the log. */ 01943 printf_filtered (_("Lowest recorded instruction number is %s.\n"), 01944 pulongest (p->u.end.insn_num)); 01945 01946 /* If in replay mode, display where we are in the log. */ 01947 if (RECORD_FULL_IS_REPLAY) 01948 printf_filtered (_("Current instruction number is %s.\n"), 01949 pulongest (record_full_list->u.end.insn_num)); 01950 01951 /* Display instruction number for last instruction in the log. */ 01952 printf_filtered (_("Highest recorded instruction number is %s.\n"), 01953 pulongest (record_full_insn_count)); 01954 01955 /* Display log count. */ 01956 printf_filtered (_("Log contains %u instructions.\n"), 01957 record_full_insn_num); 01958 } 01959 else 01960 printf_filtered (_("No instructions have been logged.\n")); 01961 01962 /* Display max log size. */ 01963 printf_filtered (_("Max logged instructions is %u.\n"), 01964 record_full_insn_max_num); 01965 } 01966 01967 /* The "to_record_delete" target method. */ 01968 01969 static void 01970 record_full_delete (void) 01971 { 01972 record_full_list_release_following (record_full_list); 01973 } 01974 01975 /* The "to_record_is_replaying" target method. */ 01976 01977 static int 01978 record_full_is_replaying (void) 01979 { 01980 return RECORD_FULL_IS_REPLAY; 01981 } 01982 01983 /* Go to a specific entry. */ 01984 01985 static void 01986 record_full_goto_entry (struct record_full_entry *p) 01987 { 01988 if (p == NULL) 01989 error (_("Target insn not found.")); 01990 else if (p == record_full_list) 01991 error (_("Already at target insn.")); 01992 else if (p->u.end.insn_num > record_full_list->u.end.insn_num) 01993 { 01994 printf_filtered (_("Go forward to insn number %s\n"), 01995 pulongest (p->u.end.insn_num)); 01996 record_full_goto_insn (p, EXEC_FORWARD); 01997 } 01998 else 01999 { 02000 printf_filtered (_("Go backward to insn number %s\n"), 02001 pulongest (p->u.end.insn_num)); 02002 record_full_goto_insn (p, EXEC_REVERSE); 02003 } 02004 02005 registers_changed (); 02006 reinit_frame_cache (); 02007 print_stack_frame (get_selected_frame (NULL), 1, SRC_AND_LOC, 1); 02008 } 02009 02010 /* The "to_goto_record_begin" target method. */ 02011 02012 static void 02013 record_full_goto_begin (void) 02014 { 02015 struct record_full_entry *p = NULL; 02016 02017 for (p = &record_full_first; p != NULL; p = p->next) 02018 if (p->type == record_full_end) 02019 break; 02020 02021 record_full_goto_entry (p); 02022 } 02023 02024 /* The "to_goto_record_end" target method. */ 02025 02026 static void 02027 record_full_goto_end (void) 02028 { 02029 struct record_full_entry *p = NULL; 02030 02031 for (p = record_full_list; p->next != NULL; p = p->next) 02032 ; 02033 for (; p!= NULL; p = p->prev) 02034 if (p->type == record_full_end) 02035 break; 02036 02037 record_full_goto_entry (p); 02038 } 02039 02040 /* The "to_goto_record" target method. */ 02041 02042 static void 02043 record_full_goto (ULONGEST target_insn) 02044 { 02045 struct record_full_entry *p = NULL; 02046 02047 for (p = &record_full_first; p != NULL; p = p->next) 02048 if (p->type == record_full_end && p->u.end.insn_num == target_insn) 02049 break; 02050 02051 record_full_goto_entry (p); 02052 } 02053 02054 static void 02055 init_record_full_ops (void) 02056 { 02057 record_full_ops.to_shortname = "record-full"; 02058 record_full_ops.to_longname = "Process record and replay target"; 02059 record_full_ops.to_doc = 02060 "Log program while executing and replay execution from log."; 02061 record_full_ops.to_open = record_full_open; 02062 record_full_ops.to_close = record_full_close; 02063 record_full_ops.to_resume = record_full_resume; 02064 record_full_ops.to_wait = record_full_wait; 02065 record_full_ops.to_disconnect = record_disconnect; 02066 record_full_ops.to_detach = record_detach; 02067 record_full_ops.to_mourn_inferior = record_mourn_inferior; 02068 record_full_ops.to_kill = record_kill; 02069 record_full_ops.to_create_inferior = find_default_create_inferior; 02070 record_full_ops.to_store_registers = record_full_store_registers; 02071 record_full_ops.to_xfer_partial = record_full_xfer_partial; 02072 record_full_ops.to_insert_breakpoint = record_full_insert_breakpoint; 02073 record_full_ops.to_remove_breakpoint = record_full_remove_breakpoint; 02074 record_full_ops.to_stopped_by_watchpoint = record_full_stopped_by_watchpoint; 02075 record_full_ops.to_stopped_data_address = record_full_stopped_data_address; 02076 record_full_ops.to_can_execute_reverse = record_full_can_execute_reverse; 02077 record_full_ops.to_stratum = record_stratum; 02078 /* Add bookmark target methods. */ 02079 record_full_ops.to_get_bookmark = record_full_get_bookmark; 02080 record_full_ops.to_goto_bookmark = record_full_goto_bookmark; 02081 record_full_ops.to_async = record_full_async; 02082 record_full_ops.to_can_async_p = record_full_can_async_p; 02083 record_full_ops.to_is_async_p = record_full_is_async_p; 02084 record_full_ops.to_execution_direction = record_full_execution_direction; 02085 record_full_ops.to_info_record = record_full_info; 02086 record_full_ops.to_save_record = record_full_save; 02087 record_full_ops.to_delete_record = record_full_delete; 02088 record_full_ops.to_record_is_replaying = record_full_is_replaying; 02089 record_full_ops.to_goto_record_begin = record_full_goto_begin; 02090 record_full_ops.to_goto_record_end = record_full_goto_end; 02091 record_full_ops.to_goto_record = record_full_goto; 02092 record_full_ops.to_magic = OPS_MAGIC; 02093 } 02094 02095 /* "to_resume" method for prec over corefile. */ 02096 02097 static void 02098 record_full_core_resume (struct target_ops *ops, ptid_t ptid, int step, 02099 enum gdb_signal signal) 02100 { 02101 record_full_resume_step = step; 02102 record_full_resumed = 1; 02103 record_full_execution_dir = execution_direction; 02104 02105 /* We are about to start executing the inferior (or simulate it), 02106 let's register it with the event loop. */ 02107 if (target_can_async_p ()) 02108 { 02109 target_async (inferior_event_handler, 0); 02110 02111 /* Notify the event loop there's an event to wait for. */ 02112 mark_async_event_handler (record_full_async_inferior_event_token); 02113 } 02114 } 02115 02116 /* "to_kill" method for prec over corefile. */ 02117 02118 static void 02119 record_full_core_kill (struct target_ops *ops) 02120 { 02121 if (record_debug) 02122 fprintf_unfiltered (gdb_stdlog, "Process record: record_full_core_kill\n"); 02123 02124 unpush_target (&record_full_core_ops); 02125 } 02126 02127 /* "to_fetch_registers" method for prec over corefile. */ 02128 02129 static void 02130 record_full_core_fetch_registers (struct target_ops *ops, 02131 struct regcache *regcache, 02132 int regno) 02133 { 02134 if (regno < 0) 02135 { 02136 int num = gdbarch_num_regs (get_regcache_arch (regcache)); 02137 int i; 02138 02139 for (i = 0; i < num; i ++) 02140 regcache_raw_supply (regcache, i, 02141 record_full_core_regbuf + MAX_REGISTER_SIZE * i); 02142 } 02143 else 02144 regcache_raw_supply (regcache, regno, 02145 record_full_core_regbuf + MAX_REGISTER_SIZE * regno); 02146 } 02147 02148 /* "to_prepare_to_store" method for prec over corefile. */ 02149 02150 static void 02151 record_full_core_prepare_to_store (struct regcache *regcache) 02152 { 02153 } 02154 02155 /* "to_store_registers" method for prec over corefile. */ 02156 02157 static void 02158 record_full_core_store_registers (struct target_ops *ops, 02159 struct regcache *regcache, 02160 int regno) 02161 { 02162 if (record_full_gdb_operation_disable) 02163 regcache_raw_collect (regcache, regno, 02164 record_full_core_regbuf + MAX_REGISTER_SIZE * regno); 02165 else 02166 error (_("You can't do that without a process to debug.")); 02167 } 02168 02169 /* "to_xfer_partial" method for prec over corefile. */ 02170 02171 static LONGEST 02172 record_full_core_xfer_partial (struct target_ops *ops, 02173 enum target_object object, 02174 const char *annex, gdb_byte *readbuf, 02175 const gdb_byte *writebuf, ULONGEST offset, 02176 LONGEST len) 02177 { 02178 if (object == TARGET_OBJECT_MEMORY) 02179 { 02180 if (record_full_gdb_operation_disable || !writebuf) 02181 { 02182 struct target_section *p; 02183 02184 for (p = record_full_core_start; p < record_full_core_end; p++) 02185 { 02186 if (offset >= p->addr) 02187 { 02188 struct record_full_core_buf_entry *entry; 02189 ULONGEST sec_offset; 02190 02191 if (offset >= p->endaddr) 02192 continue; 02193 02194 if (offset + len > p->endaddr) 02195 len = p->endaddr - offset; 02196 02197 sec_offset = offset - p->addr; 02198 02199 /* Read readbuf or write writebuf p, offset, len. */ 02200 /* Check flags. */ 02201 if (p->the_bfd_section->flags & SEC_CONSTRUCTOR 02202 || (p->the_bfd_section->flags & SEC_HAS_CONTENTS) == 0) 02203 { 02204 if (readbuf) 02205 memset (readbuf, 0, len); 02206 return len; 02207 } 02208 /* Get record_full_core_buf_entry. */ 02209 for (entry = record_full_core_buf_list; entry; 02210 entry = entry->prev) 02211 if (entry->p == p) 02212 break; 02213 if (writebuf) 02214 { 02215 if (!entry) 02216 { 02217 /* Add a new entry. */ 02218 entry = (struct record_full_core_buf_entry *) 02219 xmalloc 02220 (sizeof (struct record_full_core_buf_entry)); 02221 entry->p = p; 02222 if (!bfd_malloc_and_get_section 02223 (p->the_bfd_section->owner, 02224 p->the_bfd_section, 02225 &entry->buf)) 02226 { 02227 xfree (entry); 02228 return 0; 02229 } 02230 entry->prev = record_full_core_buf_list; 02231 record_full_core_buf_list = entry; 02232 } 02233 02234 memcpy (entry->buf + sec_offset, writebuf, 02235 (size_t) len); 02236 } 02237 else 02238 { 02239 if (!entry) 02240 return record_full_beneath_to_xfer_partial 02241 (record_full_beneath_to_xfer_partial_ops, 02242 object, annex, readbuf, writebuf, 02243 offset, len); 02244 02245 memcpy (readbuf, entry->buf + sec_offset, 02246 (size_t) len); 02247 } 02248 02249 return len; 02250 } 02251 } 02252 02253 return -1; 02254 } 02255 else 02256 error (_("You can't do that without a process to debug.")); 02257 } 02258 02259 return record_full_beneath_to_xfer_partial 02260 (record_full_beneath_to_xfer_partial_ops, object, annex, 02261 readbuf, writebuf, offset, len); 02262 } 02263 02264 /* "to_insert_breakpoint" method for prec over corefile. */ 02265 02266 static int 02267 record_full_core_insert_breakpoint (struct gdbarch *gdbarch, 02268 struct bp_target_info *bp_tgt) 02269 { 02270 return 0; 02271 } 02272 02273 /* "to_remove_breakpoint" method for prec over corefile. */ 02274 02275 static int 02276 record_full_core_remove_breakpoint (struct gdbarch *gdbarch, 02277 struct bp_target_info *bp_tgt) 02278 { 02279 return 0; 02280 } 02281 02282 /* "to_has_execution" method for prec over corefile. */ 02283 02284 static int 02285 record_full_core_has_execution (struct target_ops *ops, ptid_t the_ptid) 02286 { 02287 return 1; 02288 } 02289 02290 static void 02291 init_record_full_core_ops (void) 02292 { 02293 record_full_core_ops.to_shortname = "record-core"; 02294 record_full_core_ops.to_longname = "Process record and replay target"; 02295 record_full_core_ops.to_doc = 02296 "Log program while executing and replay execution from log."; 02297 record_full_core_ops.to_open = record_full_open; 02298 record_full_core_ops.to_close = record_full_close; 02299 record_full_core_ops.to_resume = record_full_core_resume; 02300 record_full_core_ops.to_wait = record_full_wait; 02301 record_full_core_ops.to_kill = record_full_core_kill; 02302 record_full_core_ops.to_fetch_registers = record_full_core_fetch_registers; 02303 record_full_core_ops.to_prepare_to_store = record_full_core_prepare_to_store; 02304 record_full_core_ops.to_store_registers = record_full_core_store_registers; 02305 record_full_core_ops.to_xfer_partial = record_full_core_xfer_partial; 02306 record_full_core_ops.to_insert_breakpoint 02307 = record_full_core_insert_breakpoint; 02308 record_full_core_ops.to_remove_breakpoint 02309 = record_full_core_remove_breakpoint; 02310 record_full_core_ops.to_stopped_by_watchpoint 02311 = record_full_stopped_by_watchpoint; 02312 record_full_core_ops.to_stopped_data_address 02313 = record_full_stopped_data_address; 02314 record_full_core_ops.to_can_execute_reverse 02315 = record_full_can_execute_reverse; 02316 record_full_core_ops.to_has_execution = record_full_core_has_execution; 02317 record_full_core_ops.to_stratum = record_stratum; 02318 /* Add bookmark target methods. */ 02319 record_full_core_ops.to_get_bookmark = record_full_get_bookmark; 02320 record_full_core_ops.to_goto_bookmark = record_full_goto_bookmark; 02321 record_full_core_ops.to_async = record_full_async; 02322 record_full_core_ops.to_can_async_p = record_full_can_async_p; 02323 record_full_core_ops.to_is_async_p = record_full_is_async_p; 02324 record_full_core_ops.to_execution_direction 02325 = record_full_execution_direction; 02326 record_full_core_ops.to_info_record = record_full_info; 02327 record_full_core_ops.to_delete_record = record_full_delete; 02328 record_full_core_ops.to_record_is_replaying = record_full_is_replaying; 02329 record_full_core_ops.to_goto_record_begin = record_full_goto_begin; 02330 record_full_core_ops.to_goto_record_end = record_full_goto_end; 02331 record_full_core_ops.to_goto_record = record_full_goto; 02332 record_full_core_ops.to_magic = OPS_MAGIC; 02333 } 02334 02335 /* Record log save-file format 02336 Version 1 (never released) 02337 02338 Header: 02339 4 bytes: magic number htonl(0x20090829). 02340 NOTE: be sure to change whenever this file format changes! 02341 02342 Records: 02343 record_full_end: 02344 1 byte: record type (record_full_end, see enum record_full_type). 02345 record_full_reg: 02346 1 byte: record type (record_full_reg, see enum record_full_type). 02347 8 bytes: register id (network byte order). 02348 MAX_REGISTER_SIZE bytes: register value. 02349 record_full_mem: 02350 1 byte: record type (record_full_mem, see enum record_full_type). 02351 8 bytes: memory length (network byte order). 02352 8 bytes: memory address (network byte order). 02353 n bytes: memory value (n == memory length). 02354 02355 Version 2 02356 4 bytes: magic number netorder32(0x20091016). 02357 NOTE: be sure to change whenever this file format changes! 02358 02359 Records: 02360 record_full_end: 02361 1 byte: record type (record_full_end, see enum record_full_type). 02362 4 bytes: signal 02363 4 bytes: instruction count 02364 record_full_reg: 02365 1 byte: record type (record_full_reg, see enum record_full_type). 02366 4 bytes: register id (network byte order). 02367 n bytes: register value (n == actual register size). 02368 (eg. 4 bytes for x86 general registers). 02369 record_full_mem: 02370 1 byte: record type (record_full_mem, see enum record_full_type). 02371 4 bytes: memory length (network byte order). 02372 8 bytes: memory address (network byte order). 02373 n bytes: memory value (n == memory length). 02374 02375 */ 02376 02377 /* bfdcore_read -- read bytes from a core file section. */ 02378 02379 static inline void 02380 bfdcore_read (bfd *obfd, asection *osec, void *buf, int len, int *offset) 02381 { 02382 int ret = bfd_get_section_contents (obfd, osec, buf, *offset, len); 02383 02384 if (ret) 02385 *offset += len; 02386 else 02387 error (_("Failed to read %d bytes from core file %s ('%s')."), 02388 len, bfd_get_filename (obfd), 02389 bfd_errmsg (bfd_get_error ())); 02390 } 02391 02392 static inline uint64_t 02393 netorder64 (uint64_t input) 02394 { 02395 uint64_t ret; 02396 02397 store_unsigned_integer ((gdb_byte *) &ret, sizeof (ret), 02398 BFD_ENDIAN_BIG, input); 02399 return ret; 02400 } 02401 02402 static inline uint32_t 02403 netorder32 (uint32_t input) 02404 { 02405 uint32_t ret; 02406 02407 store_unsigned_integer ((gdb_byte *) &ret, sizeof (ret), 02408 BFD_ENDIAN_BIG, input); 02409 return ret; 02410 } 02411 02412 static inline uint16_t 02413 netorder16 (uint16_t input) 02414 { 02415 uint16_t ret; 02416 02417 store_unsigned_integer ((gdb_byte *) &ret, sizeof (ret), 02418 BFD_ENDIAN_BIG, input); 02419 return ret; 02420 } 02421 02422 /* Restore the execution log from a core_bfd file. */ 02423 static void 02424 record_full_restore (void) 02425 { 02426 uint32_t magic; 02427 struct cleanup *old_cleanups; 02428 struct record_full_entry *rec; 02429 asection *osec; 02430 uint32_t osec_size; 02431 int bfd_offset = 0; 02432 struct regcache *regcache; 02433 02434 /* We restore the execution log from the open core bfd, 02435 if there is one. */ 02436 if (core_bfd == NULL) 02437 return; 02438 02439 /* "record_full_restore" can only be called when record list is empty. */ 02440 gdb_assert (record_full_first.next == NULL); 02441 02442 if (record_debug) 02443 fprintf_unfiltered (gdb_stdlog, "Restoring recording from core file.\n"); 02444 02445 /* Now need to find our special note section. */ 02446 osec = bfd_get_section_by_name (core_bfd, "null0"); 02447 if (record_debug) 02448 fprintf_unfiltered (gdb_stdlog, "Find precord section %s.\n", 02449 osec ? "succeeded" : "failed"); 02450 if (osec == NULL) 02451 return; 02452 osec_size = bfd_section_size (core_bfd, osec); 02453 if (record_debug) 02454 fprintf_unfiltered (gdb_stdlog, "%s", bfd_section_name (core_bfd, osec)); 02455 02456 /* Check the magic code. */ 02457 bfdcore_read (core_bfd, osec, &magic, sizeof (magic), &bfd_offset); 02458 if (magic != RECORD_FULL_FILE_MAGIC) 02459 error (_("Version mis-match or file format error in core file %s."), 02460 bfd_get_filename (core_bfd)); 02461 if (record_debug) 02462 fprintf_unfiltered (gdb_stdlog, 02463 " Reading 4-byte magic cookie " 02464 "RECORD_FULL_FILE_MAGIC (0x%s)\n", 02465 phex_nz (netorder32 (magic), 4)); 02466 02467 /* Restore the entries in recfd into record_full_arch_list_head and 02468 record_full_arch_list_tail. */ 02469 record_full_arch_list_head = NULL; 02470 record_full_arch_list_tail = NULL; 02471 record_full_insn_num = 0; 02472 old_cleanups = make_cleanup (record_full_arch_list_cleanups, 0); 02473 regcache = get_current_regcache (); 02474 02475 while (1) 02476 { 02477 uint8_t rectype; 02478 uint32_t regnum, len, signal, count; 02479 uint64_t addr; 02480 02481 /* We are finished when offset reaches osec_size. */ 02482 if (bfd_offset >= osec_size) 02483 break; 02484 bfdcore_read (core_bfd, osec, &rectype, sizeof (rectype), &bfd_offset); 02485 02486 switch (rectype) 02487 { 02488 case record_full_reg: /* reg */ 02489 /* Get register number to regnum. */ 02490 bfdcore_read (core_bfd, osec, ®num, 02491 sizeof (regnum), &bfd_offset); 02492 regnum = netorder32 (regnum); 02493 02494 rec = record_full_reg_alloc (regcache, regnum); 02495 02496 /* Get val. */ 02497 bfdcore_read (core_bfd, osec, record_full_get_loc (rec), 02498 rec->u.reg.len, &bfd_offset); 02499 02500 if (record_debug) 02501 fprintf_unfiltered (gdb_stdlog, 02502 " Reading register %d (1 " 02503 "plus %lu plus %d bytes)\n", 02504 rec->u.reg.num, 02505 (unsigned long) sizeof (regnum), 02506 rec->u.reg.len); 02507 break; 02508 02509 case record_full_mem: /* mem */ 02510 /* Get len. */ 02511 bfdcore_read (core_bfd, osec, &len, 02512 sizeof (len), &bfd_offset); 02513 len = netorder32 (len); 02514 02515 /* Get addr. */ 02516 bfdcore_read (core_bfd, osec, &addr, 02517 sizeof (addr), &bfd_offset); 02518 addr = netorder64 (addr); 02519 02520 rec = record_full_mem_alloc (addr, len); 02521 02522 /* Get val. */ 02523 bfdcore_read (core_bfd, osec, record_full_get_loc (rec), 02524 rec->u.mem.len, &bfd_offset); 02525 02526 if (record_debug) 02527 fprintf_unfiltered (gdb_stdlog, 02528 " Reading memory %s (1 plus " 02529 "%lu plus %lu plus %d bytes)\n", 02530 paddress (get_current_arch (), 02531 rec->u.mem.addr), 02532 (unsigned long) sizeof (addr), 02533 (unsigned long) sizeof (len), 02534 rec->u.mem.len); 02535 break; 02536 02537 case record_full_end: /* end */ 02538 rec = record_full_end_alloc (); 02539 record_full_insn_num ++; 02540 02541 /* Get signal value. */ 02542 bfdcore_read (core_bfd, osec, &signal, 02543 sizeof (signal), &bfd_offset); 02544 signal = netorder32 (signal); 02545 rec->u.end.sigval = signal; 02546 02547 /* Get insn count. */ 02548 bfdcore_read (core_bfd, osec, &count, 02549 sizeof (count), &bfd_offset); 02550 count = netorder32 (count); 02551 rec->u.end.insn_num = count; 02552 record_full_insn_count = count + 1; 02553 if (record_debug) 02554 fprintf_unfiltered (gdb_stdlog, 02555 " Reading record_full_end (1 + " 02556 "%lu + %lu bytes), offset == %s\n", 02557 (unsigned long) sizeof (signal), 02558 (unsigned long) sizeof (count), 02559 paddress (get_current_arch (), 02560 bfd_offset)); 02561 break; 02562 02563 default: 02564 error (_("Bad entry type in core file %s."), 02565 bfd_get_filename (core_bfd)); 02566 break; 02567 } 02568 02569 /* Add rec to record arch list. */ 02570 record_full_arch_list_add (rec); 02571 } 02572 02573 discard_cleanups (old_cleanups); 02574 02575 /* Add record_full_arch_list_head to the end of record list. */ 02576 record_full_first.next = record_full_arch_list_head; 02577 record_full_arch_list_head->prev = &record_full_first; 02578 record_full_arch_list_tail->next = NULL; 02579 record_full_list = &record_full_first; 02580 02581 /* Update record_full_insn_max_num. */ 02582 if (record_full_insn_num > record_full_insn_max_num) 02583 { 02584 record_full_insn_max_num = record_full_insn_num; 02585 warning (_("Auto increase record/replay buffer limit to %u."), 02586 record_full_insn_max_num); 02587 } 02588 02589 /* Succeeded. */ 02590 printf_filtered (_("Restored records from core file %s.\n"), 02591 bfd_get_filename (core_bfd)); 02592 02593 print_stack_frame (get_selected_frame (NULL), 1, SRC_AND_LOC, 1); 02594 } 02595 02596 /* bfdcore_write -- write bytes into a core file section. */ 02597 02598 static inline void 02599 bfdcore_write (bfd *obfd, asection *osec, void *buf, int len, int *offset) 02600 { 02601 int ret = bfd_set_section_contents (obfd, osec, buf, *offset, len); 02602 02603 if (ret) 02604 *offset += len; 02605 else 02606 error (_("Failed to write %d bytes to core file %s ('%s')."), 02607 len, bfd_get_filename (obfd), 02608 bfd_errmsg (bfd_get_error ())); 02609 } 02610 02611 /* Restore the execution log from a file. We use a modified elf 02612 corefile format, with an extra section for our data. */ 02613 02614 static void 02615 cmd_record_full_restore (char *args, int from_tty) 02616 { 02617 core_file_command (args, from_tty); 02618 record_full_open (args, from_tty); 02619 } 02620 02621 static void 02622 record_full_save_cleanups (void *data) 02623 { 02624 bfd *obfd = data; 02625 char *pathname = xstrdup (bfd_get_filename (obfd)); 02626 02627 gdb_bfd_unref (obfd); 02628 unlink (pathname); 02629 xfree (pathname); 02630 } 02631 02632 /* Save the execution log to a file. We use a modified elf corefile 02633 format, with an extra section for our data. */ 02634 02635 static void 02636 record_full_save (const char *recfilename) 02637 { 02638 struct record_full_entry *cur_record_full_list; 02639 uint32_t magic; 02640 struct regcache *regcache; 02641 struct gdbarch *gdbarch; 02642 struct cleanup *old_cleanups; 02643 struct cleanup *set_cleanups; 02644 bfd *obfd; 02645 int save_size = 0; 02646 asection *osec = NULL; 02647 int bfd_offset = 0; 02648 02649 /* Open the save file. */ 02650 if (record_debug) 02651 fprintf_unfiltered (gdb_stdlog, "Saving execution log to core file '%s'\n", 02652 recfilename); 02653 02654 /* Open the output file. */ 02655 obfd = create_gcore_bfd (recfilename); 02656 old_cleanups = make_cleanup (record_full_save_cleanups, obfd); 02657 02658 /* Save the current record entry to "cur_record_full_list". */ 02659 cur_record_full_list = record_full_list; 02660 02661 /* Get the values of regcache and gdbarch. */ 02662 regcache = get_current_regcache (); 02663 gdbarch = get_regcache_arch (regcache); 02664 02665 /* Disable the GDB operation record. */ 02666 set_cleanups = record_full_gdb_operation_disable_set (); 02667 02668 /* Reverse execute to the begin of record list. */ 02669 while (1) 02670 { 02671 /* Check for beginning and end of log. */ 02672 if (record_full_list == &record_full_first) 02673 break; 02674 02675 record_full_exec_insn (regcache, gdbarch, record_full_list); 02676 02677 if (record_full_list->prev) 02678 record_full_list = record_full_list->prev; 02679 } 02680 02681 /* Compute the size needed for the extra bfd section. */ 02682 save_size = 4; /* magic cookie */ 02683 for (record_full_list = record_full_first.next; record_full_list; 02684 record_full_list = record_full_list->next) 02685 switch (record_full_list->type) 02686 { 02687 case record_full_end: 02688 save_size += 1 + 4 + 4; 02689 break; 02690 case record_full_reg: 02691 save_size += 1 + 4 + record_full_list->u.reg.len; 02692 break; 02693 case record_full_mem: 02694 save_size += 1 + 4 + 8 + record_full_list->u.mem.len; 02695 break; 02696 } 02697 02698 /* Make the new bfd section. */ 02699 osec = bfd_make_section_anyway_with_flags (obfd, "precord", 02700 SEC_HAS_CONTENTS 02701 | SEC_READONLY); 02702 if (osec == NULL) 02703 error (_("Failed to create 'precord' section for corefile %s: %s"), 02704 recfilename, 02705 bfd_errmsg (bfd_get_error ())); 02706 bfd_set_section_size (obfd, osec, save_size); 02707 bfd_set_section_vma (obfd, osec, 0); 02708 bfd_set_section_alignment (obfd, osec, 0); 02709 bfd_section_lma (obfd, osec) = 0; 02710 02711 /* Save corefile state. */ 02712 write_gcore_file (obfd); 02713 02714 /* Write out the record log. */ 02715 /* Write the magic code. */ 02716 magic = RECORD_FULL_FILE_MAGIC; 02717 if (record_debug) 02718 fprintf_unfiltered (gdb_stdlog, 02719 " Writing 4-byte magic cookie " 02720 "RECORD_FULL_FILE_MAGIC (0x%s)\n", 02721 phex_nz (magic, 4)); 02722 bfdcore_write (obfd, osec, &magic, sizeof (magic), &bfd_offset); 02723 02724 /* Save the entries to recfd and forward execute to the end of 02725 record list. */ 02726 record_full_list = &record_full_first; 02727 while (1) 02728 { 02729 /* Save entry. */ 02730 if (record_full_list != &record_full_first) 02731 { 02732 uint8_t type; 02733 uint32_t regnum, len, signal, count; 02734 uint64_t addr; 02735 02736 type = record_full_list->type; 02737 bfdcore_write (obfd, osec, &type, sizeof (type), &bfd_offset); 02738 02739 switch (record_full_list->type) 02740 { 02741 case record_full_reg: /* reg */ 02742 if (record_debug) 02743 fprintf_unfiltered (gdb_stdlog, 02744 " Writing register %d (1 " 02745 "plus %lu plus %d bytes)\n", 02746 record_full_list->u.reg.num, 02747 (unsigned long) sizeof (regnum), 02748 record_full_list->u.reg.len); 02749 02750 /* Write regnum. */ 02751 regnum = netorder32 (record_full_list->u.reg.num); 02752 bfdcore_write (obfd, osec, ®num, 02753 sizeof (regnum), &bfd_offset); 02754 02755 /* Write regval. */ 02756 bfdcore_write (obfd, osec, 02757 record_full_get_loc (record_full_list), 02758 record_full_list->u.reg.len, &bfd_offset); 02759 break; 02760 02761 case record_full_mem: /* mem */ 02762 if (record_debug) 02763 fprintf_unfiltered (gdb_stdlog, 02764 " Writing memory %s (1 plus " 02765 "%lu plus %lu plus %d bytes)\n", 02766 paddress (gdbarch, 02767 record_full_list->u.mem.addr), 02768 (unsigned long) sizeof (addr), 02769 (unsigned long) sizeof (len), 02770 record_full_list->u.mem.len); 02771 02772 /* Write memlen. */ 02773 len = netorder32 (record_full_list->u.mem.len); 02774 bfdcore_write (obfd, osec, &len, sizeof (len), &bfd_offset); 02775 02776 /* Write memaddr. */ 02777 addr = netorder64 (record_full_list->u.mem.addr); 02778 bfdcore_write (obfd, osec, &addr, 02779 sizeof (addr), &bfd_offset); 02780 02781 /* Write memval. */ 02782 bfdcore_write (obfd, osec, 02783 record_full_get_loc (record_full_list), 02784 record_full_list->u.mem.len, &bfd_offset); 02785 break; 02786 02787 case record_full_end: 02788 if (record_debug) 02789 fprintf_unfiltered (gdb_stdlog, 02790 " Writing record_full_end (1 + " 02791 "%lu + %lu bytes)\n", 02792 (unsigned long) sizeof (signal), 02793 (unsigned long) sizeof (count)); 02794 /* Write signal value. */ 02795 signal = netorder32 (record_full_list->u.end.sigval); 02796 bfdcore_write (obfd, osec, &signal, 02797 sizeof (signal), &bfd_offset); 02798 02799 /* Write insn count. */ 02800 count = netorder32 (record_full_list->u.end.insn_num); 02801 bfdcore_write (obfd, osec, &count, 02802 sizeof (count), &bfd_offset); 02803 break; 02804 } 02805 } 02806 02807 /* Execute entry. */ 02808 record_full_exec_insn (regcache, gdbarch, record_full_list); 02809 02810 if (record_full_list->next) 02811 record_full_list = record_full_list->next; 02812 else 02813 break; 02814 } 02815 02816 /* Reverse execute to cur_record_full_list. */ 02817 while (1) 02818 { 02819 /* Check for beginning and end of log. */ 02820 if (record_full_list == cur_record_full_list) 02821 break; 02822 02823 record_full_exec_insn (regcache, gdbarch, record_full_list); 02824 02825 if (record_full_list->prev) 02826 record_full_list = record_full_list->prev; 02827 } 02828 02829 do_cleanups (set_cleanups); 02830 gdb_bfd_unref (obfd); 02831 discard_cleanups (old_cleanups); 02832 02833 /* Succeeded. */ 02834 printf_filtered (_("Saved core file %s with execution log.\n"), 02835 recfilename); 02836 } 02837 02838 /* record_full_goto_insn -- rewind the record log (forward or backward, 02839 depending on DIR) to the given entry, changing the program state 02840 correspondingly. */ 02841 02842 static void 02843 record_full_goto_insn (struct record_full_entry *entry, 02844 enum exec_direction_kind dir) 02845 { 02846 struct cleanup *set_cleanups = record_full_gdb_operation_disable_set (); 02847 struct regcache *regcache = get_current_regcache (); 02848 struct gdbarch *gdbarch = get_regcache_arch (regcache); 02849 02850 /* Assume everything is valid: we will hit the entry, 02851 and we will not hit the end of the recording. */ 02852 02853 if (dir == EXEC_FORWARD) 02854 record_full_list = record_full_list->next; 02855 02856 do 02857 { 02858 record_full_exec_insn (regcache, gdbarch, record_full_list); 02859 if (dir == EXEC_REVERSE) 02860 record_full_list = record_full_list->prev; 02861 else 02862 record_full_list = record_full_list->next; 02863 } while (record_full_list != entry); 02864 do_cleanups (set_cleanups); 02865 } 02866 02867 /* Alias for "target record-full". */ 02868 02869 static void 02870 cmd_record_full_start (char *args, int from_tty) 02871 { 02872 execute_command ("target record-full", from_tty); 02873 } 02874 02875 static void 02876 set_record_full_insn_max_num (char *args, int from_tty, 02877 struct cmd_list_element *c) 02878 { 02879 if (record_full_insn_num > record_full_insn_max_num) 02880 { 02881 /* Count down record_full_insn_num while releasing records from list. */ 02882 while (record_full_insn_num > record_full_insn_max_num) 02883 { 02884 record_full_list_release_first (); 02885 record_full_insn_num--; 02886 } 02887 } 02888 } 02889 02890 /* The "set record full" command. */ 02891 02892 static void 02893 set_record_full_command (char *args, int from_tty) 02894 { 02895 printf_unfiltered (_("\"set record full\" must be followed " 02896 "by an apporpriate subcommand.\n")); 02897 help_list (set_record_full_cmdlist, "set record full ", all_commands, 02898 gdb_stdout); 02899 } 02900 02901 /* The "show record full" command. */ 02902 02903 static void 02904 show_record_full_command (char *args, int from_tty) 02905 { 02906 cmd_show_list (show_record_full_cmdlist, from_tty, ""); 02907 } 02908 02909 /* Provide a prototype to silence -Wmissing-prototypes. */ 02910 extern initialize_file_ftype _initialize_record_full; 02911 02912 void 02913 _initialize_record_full (void) 02914 { 02915 struct cmd_list_element *c; 02916 02917 /* Init record_full_first. */ 02918 record_full_first.prev = NULL; 02919 record_full_first.next = NULL; 02920 record_full_first.type = record_full_end; 02921 02922 init_record_full_ops (); 02923 add_target (&record_full_ops); 02924 add_deprecated_target_alias (&record_full_ops, "record"); 02925 init_record_full_core_ops (); 02926 add_target (&record_full_core_ops); 02927 02928 add_prefix_cmd ("full", class_obscure, cmd_record_full_start, 02929 _("Start full execution recording."), &record_full_cmdlist, 02930 "record full ", 0, &record_cmdlist); 02931 02932 c = add_cmd ("restore", class_obscure, cmd_record_full_restore, 02933 _("Restore the execution log from a file.\n\ 02934 Argument is filename. File must be created with 'record save'."), 02935 &record_full_cmdlist); 02936 set_cmd_completer (c, filename_completer); 02937 02938 /* Deprecate the old version without "full" prefix. */ 02939 c = add_alias_cmd ("restore", "full restore", class_obscure, 1, 02940 &record_cmdlist); 02941 set_cmd_completer (c, filename_completer); 02942 deprecate_cmd (c, "record full restore"); 02943 02944 add_prefix_cmd ("full", class_support, set_record_full_command, 02945 _("Set record options"), &set_record_full_cmdlist, 02946 "set record full ", 0, &set_record_cmdlist); 02947 02948 add_prefix_cmd ("full", class_support, show_record_full_command, 02949 _("Show record options"), &show_record_full_cmdlist, 02950 "show record full ", 0, &show_record_cmdlist); 02951 02952 /* Record instructions number limit command. */ 02953 add_setshow_boolean_cmd ("stop-at-limit", no_class, 02954 &record_full_stop_at_limit, _("\ 02955 Set whether record/replay stops when record/replay buffer becomes full."), _("\ 02956 Show whether record/replay stops when record/replay buffer becomes full."), 02957 _("Default is ON.\n\ 02958 When ON, if the record/replay buffer becomes full, ask user what to do.\n\ 02959 When OFF, if the record/replay buffer becomes full,\n\ 02960 delete the oldest recorded instruction to make room for each new one."), 02961 NULL, NULL, 02962 &set_record_full_cmdlist, &show_record_full_cmdlist); 02963 02964 c = add_alias_cmd ("stop-at-limit", "full stop-at-limit", no_class, 1, 02965 &set_record_cmdlist); 02966 deprecate_cmd (c, "set record full stop-at-limit"); 02967 02968 c = add_alias_cmd ("stop-at-limit", "full stop-at-limit", no_class, 1, 02969 &show_record_cmdlist); 02970 deprecate_cmd (c, "show record full stop-at-limit"); 02971 02972 add_setshow_uinteger_cmd ("insn-number-max", no_class, 02973 &record_full_insn_max_num, 02974 _("Set record/replay buffer limit."), 02975 _("Show record/replay buffer limit."), _("\ 02976 Set the maximum number of instructions to be stored in the\n\ 02977 record/replay buffer. A value of either \"unlimited\" or zero means no\n\ 02978 limit. Default is 200000."), 02979 set_record_full_insn_max_num, 02980 NULL, &set_record_full_cmdlist, 02981 &show_record_full_cmdlist); 02982 02983 c = add_alias_cmd ("insn-number-max", "full insn-number-max", no_class, 1, 02984 &set_record_cmdlist); 02985 deprecate_cmd (c, "set record full insn-number-max"); 02986 02987 c = add_alias_cmd ("insn-number-max", "full insn-number-max", no_class, 1, 02988 &show_record_cmdlist); 02989 deprecate_cmd (c, "show record full insn-number-max"); 02990 02991 add_setshow_boolean_cmd ("memory-query", no_class, 02992 &record_full_memory_query, _("\ 02993 Set whether query if PREC cannot record memory change of next instruction."), 02994 _("\ 02995 Show whether query if PREC cannot record memory change of next instruction."), 02996 _("\ 02997 Default is OFF.\n\ 02998 When ON, query if PREC cannot record memory change of next instruction."), 02999 NULL, NULL, 03000 &set_record_full_cmdlist, 03001 &show_record_full_cmdlist); 03002 03003 c = add_alias_cmd ("memory-query", "full memory-query", no_class, 1, 03004 &set_record_cmdlist); 03005 deprecate_cmd (c, "set record full memory-query"); 03006 03007 c = add_alias_cmd ("memory-query", "full memory-query", no_class, 1, 03008 &show_record_cmdlist); 03009 deprecate_cmd (c, "show record full memory-query"); 03010 }