]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blame - gdb/gdbserver/mem-break.c
Add missing files from previous commit.
[thirdparty/binutils-gdb.git] / gdb / gdbserver / mem-break.c
CommitLineData
611cb4a5 1/* Memory breakpoint operations for the remote server for GDB.
0b302171
JB
2 Copyright (C) 2002-2003, 2005, 2007-2012 Free Software Foundation,
3 Inc.
611cb4a5
DJ
4
5 Contributed by MontaVista Software.
6
7 This file is part of GDB.
8
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
a9762ec7 11 the Free Software Foundation; either version 3 of the License, or
611cb4a5
DJ
12 (at your option) any later version.
13
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 You should have received a copy of the GNU General Public License
a9762ec7 20 along with this program. If not, see <http://www.gnu.org/licenses/>. */
611cb4a5
DJ
21
22#include "server.h"
23
f450004a 24const unsigned char *breakpoint_data;
611cb4a5
DJ
25int breakpoint_len;
26
27#define MAX_BREAKPOINT_LEN 8
28
8b07ae33
PA
29/* GDB will never try to install multiple breakpoints at the same
30 address. But, we need to keep track of internal breakpoints too,
31 and so we do need to be able to install multiple breakpoints at the
32 same address transparently. We keep track of two different, and
33 closely related structures. A raw breakpoint, which manages the
34 low level, close to the metal aspect of a breakpoint. It holds the
35 breakpoint address, and a buffer holding a copy of the instructions
36 that would be in memory had not been a breakpoint there (we call
37 that the shadow memory of the breakpoint). We occasionally need to
38 temporarilly uninsert a breakpoint without the client knowing about
39 it (e.g., to step over an internal breakpoint), so we keep an
40 `inserted' state associated with this low level breakpoint
41 structure. There can only be one such object for a given address.
42 Then, we have (a bit higher level) breakpoints. This structure
43 holds a callback to be called whenever a breakpoint is hit, a
44 high-level type, and a link to a low level raw breakpoint. There
45 can be many high-level breakpoints at the same address, and all of
46 them will point to the same raw breakpoint, which is reference
47 counted. */
48
49/* The low level, physical, raw breakpoint. */
50struct raw_breakpoint
51{
52 struct raw_breakpoint *next;
53
54 /* A reference count. Each high level breakpoint referencing this
55 raw breakpoint accounts for one reference. */
56 int refcount;
57
58 /* The breakpoint's insertion address. There can only be one raw
59 breakpoint for a given PC. */
60 CORE_ADDR pc;
61
62 /* The breakpoint's shadow memory. */
63 unsigned char old_data[MAX_BREAKPOINT_LEN];
64
65 /* Non-zero if this breakpoint is currently inserted in the
66 inferior. */
67 int inserted;
d3bbe7a0
PA
68
69 /* Non-zero if this breakpoint is currently disabled because we no
70 longer detect it as inserted. */
71 int shlib_disabled;
8b07ae33
PA
72};
73
414a389f
PA
74/* The type of a breakpoint. */
75enum bkpt_type
76 {
8b07ae33
PA
77 /* A GDB breakpoint, requested with a Z0 packet. */
78 gdb_breakpoint,
79
414a389f
PA
80 /* A basic-software-single-step breakpoint. */
81 reinsert_breakpoint,
82
83 /* Any other breakpoint type that doesn't require specific
84 treatment goes here. E.g., an event breakpoint. */
85 other_breakpoint,
86 };
87
8b07ae33 88/* A high level (in gdbserver's perspective) breakpoint. */
611cb4a5
DJ
89struct breakpoint
90{
91 struct breakpoint *next;
611cb4a5 92
414a389f
PA
93 /* The breakpoint's type. */
94 enum bkpt_type type;
95
8b07ae33
PA
96 /* Link to this breakpoint's raw breakpoint. This is always
97 non-NULL. */
98 struct raw_breakpoint *raw;
99
b65d95c5 100 /* Function to call when we hit this breakpoint. If it returns 1,
8b07ae33
PA
101 the breakpoint shall be deleted; 0 or if this callback is NULL,
102 it will be left inserted. */
b65d95c5 103 int (*handler) (CORE_ADDR);
611cb4a5
DJ
104};
105
8b07ae33
PA
106static struct raw_breakpoint *
107find_raw_breakpoint_at (CORE_ADDR where)
108{
109 struct process_info *proc = current_process ();
110 struct raw_breakpoint *bp;
414a389f 111
8b07ae33
PA
112 for (bp = proc->raw_breakpoints; bp != NULL; bp = bp->next)
113 if (bp->pc == where)
114 return bp;
115
116 return NULL;
117}
118
119static struct raw_breakpoint *
d50171e4 120set_raw_breakpoint_at (CORE_ADDR where)
611cb4a5 121{
95954743 122 struct process_info *proc = current_process ();
8b07ae33 123 struct raw_breakpoint *bp;
d50171e4 124 int err;
6bf36717 125 unsigned char buf[MAX_BREAKPOINT_LEN];
611cb4a5
DJ
126
127 if (breakpoint_data == NULL)
128 error ("Target does not support breakpoints.");
129
8b07ae33
PA
130 bp = find_raw_breakpoint_at (where);
131 if (bp != NULL)
132 {
133 bp->refcount++;
134 return bp;
135 }
136
d50171e4
PA
137 bp = xcalloc (1, sizeof (*bp));
138 bp->pc = where;
8b07ae33 139 bp->refcount = 1;
611cb4a5 140
fa593d66
PA
141 /* Note that there can be fast tracepoint jumps installed in the
142 same memory range, so to get at the original memory, we need to
143 use read_inferior_memory, which masks those out. */
6bf36717 144 err = read_inferior_memory (where, buf, breakpoint_len);
d50171e4
PA
145 if (err != 0)
146 {
147 if (debug_threads)
148 fprintf (stderr,
149 "Failed to read shadow memory of"
150 " breakpoint at 0x%s (%s).\n",
151 paddress (where), strerror (err));
152 free (bp);
153 return NULL;
154 }
6bf36717 155 memcpy (bp->old_data, buf, breakpoint_len);
611cb4a5 156
d50171e4
PA
157 err = (*the_target->write_memory) (where, breakpoint_data,
158 breakpoint_len);
159 if (err != 0)
160 {
161 if (debug_threads)
162 fprintf (stderr,
163 "Failed to insert breakpoint at 0x%s (%s).\n",
164 paddress (where), strerror (err));
165 free (bp);
166 return NULL;
167 }
168
169 /* Link the breakpoint in. */
170 bp->inserted = 1;
8b07ae33
PA
171 bp->next = proc->raw_breakpoints;
172 proc->raw_breakpoints = bp;
d50171e4
PA
173 return bp;
174}
175
fa593d66
PA
176/* Notice that breakpoint traps are always installed on top of fast
177 tracepoint jumps. This is even if the fast tracepoint is installed
178 at a later time compared to when the breakpoint was installed.
179 This means that a stopping breakpoint or tracepoint has higher
180 "priority". In turn, this allows having fast and slow tracepoints
181 (and breakpoints) at the same address behave correctly. */
182
183
184/* A fast tracepoint jump. */
185
186struct fast_tracepoint_jump
187{
188 struct fast_tracepoint_jump *next;
189
190 /* A reference count. GDB can install more than one fast tracepoint
191 at the same address (each with its own action list, for
192 example). */
193 int refcount;
194
195 /* The fast tracepoint's insertion address. There can only be one
196 of these for a given PC. */
197 CORE_ADDR pc;
198
199 /* Non-zero if this fast tracepoint jump is currently inserted in
200 the inferior. */
201 int inserted;
202
203 /* The length of the jump instruction. */
204 int length;
205
206 /* A poor-man's flexible array member, holding both the jump
207 instruction to insert, and a copy of the instruction that would
208 be in memory had not been a jump there (the shadow memory of the
209 tracepoint jump). */
210 unsigned char insn_and_shadow[0];
211};
212
213/* Fast tracepoint FP's jump instruction to insert. */
214#define fast_tracepoint_jump_insn(fp) \
215 ((fp)->insn_and_shadow + 0)
216
217/* The shadow memory of fast tracepoint jump FP. */
218#define fast_tracepoint_jump_shadow(fp) \
219 ((fp)->insn_and_shadow + (fp)->length)
220
221
222/* Return the fast tracepoint jump set at WHERE. */
223
224static struct fast_tracepoint_jump *
225find_fast_tracepoint_jump_at (CORE_ADDR where)
226{
227 struct process_info *proc = current_process ();
228 struct fast_tracepoint_jump *jp;
229
230 for (jp = proc->fast_tracepoint_jumps; jp != NULL; jp = jp->next)
231 if (jp->pc == where)
232 return jp;
233
234 return NULL;
235}
236
237int
238fast_tracepoint_jump_here (CORE_ADDR where)
239{
240 struct fast_tracepoint_jump *jp = find_fast_tracepoint_jump_at (where);
241
242 return (jp != NULL);
243}
244
245int
246delete_fast_tracepoint_jump (struct fast_tracepoint_jump *todel)
247{
248 struct fast_tracepoint_jump *bp, **bp_link;
249 int ret;
250 struct process_info *proc = current_process ();
251
252 bp = proc->fast_tracepoint_jumps;
253 bp_link = &proc->fast_tracepoint_jumps;
254
255 while (bp)
256 {
257 if (bp == todel)
258 {
259 if (--bp->refcount == 0)
260 {
261 struct fast_tracepoint_jump *prev_bp_link = *bp_link;
6bf36717 262 unsigned char *buf;
fa593d66
PA
263
264 /* Unlink it. */
265 *bp_link = bp->next;
266
267 /* Since there can be breakpoints inserted in the same
268 address range, we use `write_inferior_memory', which
269 takes care of layering breakpoints on top of fast
270 tracepoints, and on top of the buffer we pass it.
271 This works because we've already unlinked the fast
272 tracepoint jump above. Also note that we need to
273 pass the current shadow contents, because
274 write_inferior_memory updates any shadow memory with
275 what we pass here, and we want that to be a nop. */
6bf36717
JK
276 buf = alloca (bp->length);
277 memcpy (buf, fast_tracepoint_jump_shadow (bp), bp->length);
278 ret = write_inferior_memory (bp->pc, buf, bp->length);
fa593d66
PA
279 if (ret != 0)
280 {
281 /* Something went wrong, relink the jump. */
282 *bp_link = prev_bp_link;
283
284 if (debug_threads)
285 fprintf (stderr,
286 "Failed to uninsert fast tracepoint jump "
287 "at 0x%s (%s) while deleting it.\n",
288 paddress (bp->pc), strerror (ret));
289 return ret;
290 }
291
292 free (bp);
293 }
294
295 return 0;
296 }
297 else
298 {
299 bp_link = &bp->next;
300 bp = *bp_link;
301 }
302 }
303
304 warning ("Could not find fast tracepoint jump in list.");
305 return ENOENT;
306}
307
5c73ff4e
YQ
308void
309inc_ref_fast_tracepoint_jump (struct fast_tracepoint_jump *jp)
310{
311 jp->refcount++;
312}
313
fa593d66
PA
314struct fast_tracepoint_jump *
315set_fast_tracepoint_jump (CORE_ADDR where,
316 unsigned char *insn, ULONGEST length)
317{
318 struct process_info *proc = current_process ();
319 struct fast_tracepoint_jump *jp;
320 int err;
6bf36717 321 unsigned char *buf;
fa593d66
PA
322
323 /* We refcount fast tracepoint jumps. Check if we already know
324 about a jump at this address. */
325 jp = find_fast_tracepoint_jump_at (where);
326 if (jp != NULL)
327 {
328 jp->refcount++;
329 return jp;
330 }
331
332 /* We don't, so create a new object. Double the length, because the
333 flexible array member holds both the jump insn, and the
334 shadow. */
335 jp = xcalloc (1, sizeof (*jp) + (length * 2));
336 jp->pc = where;
337 jp->length = length;
338 memcpy (fast_tracepoint_jump_insn (jp), insn, length);
339 jp->refcount = 1;
6bf36717 340 buf = alloca (length);
fa593d66
PA
341
342 /* Note that there can be trap breakpoints inserted in the same
343 address range. To access the original memory contents, we use
344 `read_inferior_memory', which masks out breakpoints. */
6bf36717 345 err = read_inferior_memory (where, buf, length);
fa593d66
PA
346 if (err != 0)
347 {
348 if (debug_threads)
349 fprintf (stderr,
350 "Failed to read shadow memory of"
351 " fast tracepoint at 0x%s (%s).\n",
352 paddress (where), strerror (err));
353 free (jp);
354 return NULL;
355 }
6bf36717 356 memcpy (fast_tracepoint_jump_shadow (jp), buf, length);
fa593d66
PA
357
358 /* Link the jump in. */
359 jp->inserted = 1;
360 jp->next = proc->fast_tracepoint_jumps;
361 proc->fast_tracepoint_jumps = jp;
362
363 /* Since there can be trap breakpoints inserted in the same address
364 range, we use use `write_inferior_memory', which takes care of
365 layering breakpoints on top of fast tracepoints, on top of the
366 buffer we pass it. This works because we've already linked in
367 the fast tracepoint jump above. Also note that we need to pass
368 the current shadow contents, because write_inferior_memory
369 updates any shadow memory with what we pass here, and we want
370 that to be a nop. */
6bf36717 371 err = write_inferior_memory (where, buf, length);
fa593d66
PA
372 if (err != 0)
373 {
374 if (debug_threads)
375 fprintf (stderr,
376 "Failed to insert fast tracepoint jump at 0x%s (%s).\n",
377 paddress (where), strerror (err));
378
379 /* Unlink it. */
380 proc->fast_tracepoint_jumps = jp->next;
381 free (jp);
382
383 return NULL;
384 }
385
386 return jp;
387}
388
389void
390uninsert_fast_tracepoint_jumps_at (CORE_ADDR pc)
391{
392 struct fast_tracepoint_jump *jp;
393 int err;
394
395 jp = find_fast_tracepoint_jump_at (pc);
396 if (jp == NULL)
397 {
398 /* This can happen when we remove all breakpoints while handling
399 a step-over. */
400 if (debug_threads)
401 fprintf (stderr,
402 "Could not find fast tracepoint jump at 0x%s "
403 "in list (uninserting).\n",
404 paddress (pc));
405 return;
406 }
407
408 if (jp->inserted)
409 {
6bf36717
JK
410 unsigned char *buf;
411
fa593d66
PA
412 jp->inserted = 0;
413
414 /* Since there can be trap breakpoints inserted in the same
415 address range, we use use `write_inferior_memory', which
416 takes care of layering breakpoints on top of fast
417 tracepoints, and on top of the buffer we pass it. This works
418 because we've already marked the fast tracepoint fast
419 tracepoint jump uninserted above. Also note that we need to
420 pass the current shadow contents, because
421 write_inferior_memory updates any shadow memory with what we
422 pass here, and we want that to be a nop. */
6bf36717
JK
423 buf = alloca (jp->length);
424 memcpy (buf, fast_tracepoint_jump_shadow (jp), jp->length);
425 err = write_inferior_memory (jp->pc, buf, jp->length);
fa593d66
PA
426 if (err != 0)
427 {
428 jp->inserted = 1;
429
430 if (debug_threads)
431 fprintf (stderr,
432 "Failed to uninsert fast tracepoint jump at 0x%s (%s).\n",
433 paddress (pc), strerror (err));
434 }
435 }
436}
437
438void
439reinsert_fast_tracepoint_jumps_at (CORE_ADDR where)
440{
441 struct fast_tracepoint_jump *jp;
442 int err;
6bf36717 443 unsigned char *buf;
fa593d66
PA
444
445 jp = find_fast_tracepoint_jump_at (where);
446 if (jp == NULL)
447 {
448 /* This can happen when we remove breakpoints when a tracepoint
449 hit causes a tracing stop, while handling a step-over. */
450 if (debug_threads)
451 fprintf (stderr,
452 "Could not find fast tracepoint jump at 0x%s "
453 "in list (reinserting).\n",
454 paddress (where));
455 return;
456 }
457
458 if (jp->inserted)
459 error ("Jump already inserted at reinsert time.");
460
461 jp->inserted = 1;
462
463 /* Since there can be trap breakpoints inserted in the same address
464 range, we use `write_inferior_memory', which takes care of
465 layering breakpoints on top of fast tracepoints, and on top of
466 the buffer we pass it. This works because we've already marked
467 the fast tracepoint jump inserted above. Also note that we need
468 to pass the current shadow contents, because
469 write_inferior_memory updates any shadow memory with what we pass
470 here, and we want that to be a nop. */
6bf36717
JK
471 buf = alloca (jp->length);
472 memcpy (buf, fast_tracepoint_jump_shadow (jp), jp->length);
473 err = write_inferior_memory (where, buf, jp->length);
fa593d66
PA
474 if (err != 0)
475 {
476 jp->inserted = 0;
477
478 if (debug_threads)
479 fprintf (stderr,
480 "Failed to reinsert fast tracepoint jump at 0x%s (%s).\n",
481 paddress (where), strerror (err));
482 }
483}
484
414a389f 485struct breakpoint *
d50171e4
PA
486set_breakpoint_at (CORE_ADDR where, int (*handler) (CORE_ADDR))
487{
488 struct process_info *proc = current_process ();
489 struct breakpoint *bp;
8b07ae33 490 struct raw_breakpoint *raw;
d50171e4 491
8b07ae33 492 raw = set_raw_breakpoint_at (where);
d50171e4 493
8b07ae33 494 if (raw == NULL)
d50171e4
PA
495 {
496 /* warn? */
414a389f 497 return NULL;
d50171e4
PA
498 }
499
500 bp = xcalloc (1, sizeof (struct breakpoint));
414a389f 501 bp->type = other_breakpoint;
8b07ae33
PA
502
503 bp->raw = raw;
611cb4a5
DJ
504 bp->handler = handler;
505
95954743
PA
506 bp->next = proc->breakpoints;
507 proc->breakpoints = bp;
414a389f
PA
508
509 return bp;
611cb4a5
DJ
510}
511
8b07ae33
PA
512static int
513delete_raw_breakpoint (struct process_info *proc, struct raw_breakpoint *todel)
514{
515 struct raw_breakpoint *bp, **bp_link;
516 int ret;
517
518 bp = proc->raw_breakpoints;
519 bp_link = &proc->raw_breakpoints;
520
521 while (bp)
522 {
523 if (bp == todel)
524 {
525 if (bp->inserted)
526 {
527 struct raw_breakpoint *prev_bp_link = *bp_link;
6bf36717 528 unsigned char buf[MAX_BREAKPOINT_LEN];
8b07ae33
PA
529
530 *bp_link = bp->next;
531
fa593d66
PA
532 /* Since there can be trap breakpoints inserted in the
533 same address range, we use `write_inferior_memory',
534 which takes care of layering breakpoints on top of
535 fast tracepoints, and on top of the buffer we pass
536 it. This works because we've already unlinked the
537 fast tracepoint jump above. Also note that we need
538 to pass the current shadow contents, because
539 write_inferior_memory updates any shadow memory with
540 what we pass here, and we want that to be a nop. */
6bf36717
JK
541 memcpy (buf, bp->old_data, breakpoint_len);
542 ret = write_inferior_memory (bp->pc, buf, breakpoint_len);
8b07ae33
PA
543 if (ret != 0)
544 {
545 /* Something went wrong, relink the breakpoint. */
546 *bp_link = prev_bp_link;
547
548 if (debug_threads)
549 fprintf (stderr,
550 "Failed to uninsert raw breakpoint "
551 "at 0x%s (%s) while deleting it.\n",
552 paddress (bp->pc), strerror (ret));
553 return ret;
554 }
555
556 }
557 else
558 *bp_link = bp->next;
559
560 free (bp);
561 return 0;
562 }
563 else
564 {
565 bp_link = &bp->next;
566 bp = *bp_link;
567 }
568 }
569
570 warning ("Could not find raw breakpoint in list.");
571 return ENOENT;
572}
573
574static int
575release_breakpoint (struct process_info *proc, struct breakpoint *bp)
576{
577 int newrefcount;
578 int ret;
579
580 newrefcount = bp->raw->refcount - 1;
581 if (newrefcount == 0)
582 {
583 ret = delete_raw_breakpoint (proc, bp->raw);
584 if (ret != 0)
585 return ret;
586 }
587 else
588 bp->raw->refcount = newrefcount;
589
590 free (bp);
591
592 return 0;
593}
594
595static int
596delete_breakpoint_1 (struct process_info *proc, struct breakpoint *todel)
611cb4a5 597{
414a389f 598 struct breakpoint *bp, **bp_link;
8b07ae33 599 int err;
611cb4a5 600
414a389f
PA
601 bp = proc->breakpoints;
602 bp_link = &proc->breakpoints;
603
604 while (bp)
611cb4a5 605 {
414a389f 606 if (bp == todel)
611cb4a5 607 {
414a389f
PA
608 *bp_link = bp->next;
609
8b07ae33
PA
610 err = release_breakpoint (proc, bp);
611 if (err != 0)
612 return err;
613
614 bp = *bp_link;
615 return 0;
611cb4a5 616 }
414a389f
PA
617 else
618 {
619 bp_link = &bp->next;
620 bp = *bp_link;
621 }
611cb4a5 622 }
414a389f 623
611cb4a5 624 warning ("Could not find breakpoint in list.");
8b07ae33
PA
625 return ENOENT;
626}
627
219f2f23 628int
8b07ae33
PA
629delete_breakpoint (struct breakpoint *todel)
630{
631 struct process_info *proc = current_process ();
632 return delete_breakpoint_1 (proc, todel);
611cb4a5
DJ
633}
634
635static struct breakpoint *
8b07ae33 636find_gdb_breakpoint_at (CORE_ADDR where)
611cb4a5 637{
95954743 638 struct process_info *proc = current_process ();
8b07ae33 639 struct breakpoint *bp;
611cb4a5 640
8b07ae33
PA
641 for (bp = proc->breakpoints; bp != NULL; bp = bp->next)
642 if (bp->type == gdb_breakpoint && bp->raw->pc == where)
643 return bp;
611cb4a5
DJ
644
645 return NULL;
646}
647
8b07ae33
PA
648int
649set_gdb_breakpoint_at (CORE_ADDR where)
68070c10 650{
8b07ae33
PA
651 struct breakpoint *bp;
652
653 if (breakpoint_data == NULL)
654 return 1;
655
d3bbe7a0
PA
656 /* If we see GDB inserting a second breakpoint at the same address,
657 then the first breakpoint must have disappeared due to a shared
658 library unload. On targets where the shared libraries are
659 handled by userspace, like SVR4, for example, GDBserver can't
660 tell if a library was loaded or unloaded. Since we refcount
661 breakpoints, if we didn't do this, we'd just increase the
662 refcount of the previous breakpoint at this address, but the trap
663 was not planted in the inferior anymore, thus the breakpoint
664 would never be hit. */
665 bp = find_gdb_breakpoint_at (where);
666 if (bp != NULL)
667 {
668 delete_gdb_breakpoint_at (where);
669
670 /* Might as well validate all other breakpoints. */
671 validate_breakpoints ();
672 }
673
8b07ae33
PA
674 bp = set_breakpoint_at (where, NULL);
675 if (bp == NULL)
676 return -1;
677
678 bp->type = gdb_breakpoint;
679 return 0;
680}
681
682int
683delete_gdb_breakpoint_at (CORE_ADDR addr)
684{
685 struct breakpoint *bp;
686 int err;
687
688 if (breakpoint_data == NULL)
689 return 1;
690
691 bp = find_gdb_breakpoint_at (addr);
692 if (bp == NULL)
693 return -1;
694
695 err = delete_breakpoint (bp);
696 if (err)
697 return -1;
698
699 return 0;
700}
701
702int
703gdb_breakpoint_here (CORE_ADDR where)
704{
705 struct breakpoint *bp = find_gdb_breakpoint_at (where);
706
707 return (bp != NULL);
68070c10
PA
708}
709
d50171e4
PA
710void
711set_reinsert_breakpoint (CORE_ADDR stop_at)
611cb4a5 712{
414a389f
PA
713 struct breakpoint *bp;
714
715 bp = set_breakpoint_at (stop_at, NULL);
414a389f 716 bp->type = reinsert_breakpoint;
611cb4a5
DJ
717}
718
719void
d50171e4 720delete_reinsert_breakpoints (void)
611cb4a5 721{
d50171e4
PA
722 struct process_info *proc = current_process ();
723 struct breakpoint *bp, **bp_link;
611cb4a5 724
d50171e4
PA
725 bp = proc->breakpoints;
726 bp_link = &proc->breakpoints;
611cb4a5 727
d50171e4
PA
728 while (bp)
729 {
414a389f
PA
730 if (bp->type == reinsert_breakpoint)
731 {
732 *bp_link = bp->next;
8b07ae33 733 release_breakpoint (proc, bp);
414a389f
PA
734 bp = *bp_link;
735 }
736 else
737 {
738 bp_link = &bp->next;
739 bp = *bp_link;
740 }
d50171e4
PA
741 }
742}
b65d95c5 743
d50171e4 744static void
8b07ae33 745uninsert_raw_breakpoint (struct raw_breakpoint *bp)
d50171e4
PA
746{
747 if (bp->inserted)
748 {
749 int err;
6bf36717 750 unsigned char buf[MAX_BREAKPOINT_LEN];
d50171e4
PA
751
752 bp->inserted = 0;
fa593d66
PA
753 /* Since there can be fast tracepoint jumps inserted in the same
754 address range, we use `write_inferior_memory', which takes
755 care of layering breakpoints on top of fast tracepoints, and
756 on top of the buffer we pass it. This works because we've
757 already unlinked the fast tracepoint jump above. Also note
758 that we need to pass the current shadow contents, because
759 write_inferior_memory updates any shadow memory with what we
760 pass here, and we want that to be a nop. */
6bf36717
JK
761 memcpy (buf, bp->old_data, breakpoint_len);
762 err = write_inferior_memory (bp->pc, buf, breakpoint_len);
d50171e4
PA
763 if (err != 0)
764 {
765 bp->inserted = 1;
611cb4a5 766
d50171e4
PA
767 if (debug_threads)
768 fprintf (stderr,
769 "Failed to uninsert raw breakpoint at 0x%s (%s).\n",
770 paddress (bp->pc), strerror (err));
771 }
772 }
611cb4a5
DJ
773}
774
775void
d50171e4 776uninsert_breakpoints_at (CORE_ADDR pc)
611cb4a5 777{
8b07ae33 778 struct raw_breakpoint *bp;
611cb4a5 779
8b07ae33 780 bp = find_raw_breakpoint_at (pc);
611cb4a5 781 if (bp == NULL)
d50171e4
PA
782 {
783 /* This can happen when we remove all breakpoints while handling
784 a step-over. */
785 if (debug_threads)
786 fprintf (stderr,
787 "Could not find breakpoint at 0x%s "
788 "in list (uninserting).\n",
789 paddress (pc));
790 return;
791 }
611cb4a5 792
d50171e4 793 if (bp->inserted)
8b07ae33 794 uninsert_raw_breakpoint (bp);
611cb4a5
DJ
795}
796
0fb4aa4b
PA
797void
798uninsert_all_breakpoints (void)
799{
800 struct process_info *proc = current_process ();
801 struct raw_breakpoint *bp;
802
803 for (bp = proc->raw_breakpoints; bp != NULL; bp = bp->next)
804 if (bp->inserted)
805 uninsert_raw_breakpoint (bp);
806}
807
d50171e4 808static void
8b07ae33 809reinsert_raw_breakpoint (struct raw_breakpoint *bp)
611cb4a5 810{
d50171e4 811 int err;
611cb4a5 812
d50171e4 813 if (bp->inserted)
611cb4a5
DJ
814 error ("Breakpoint already inserted at reinsert time.");
815
d50171e4
PA
816 err = (*the_target->write_memory) (bp->pc, breakpoint_data,
817 breakpoint_len);
818 if (err == 0)
819 bp->inserted = 1;
820 else if (debug_threads)
821 fprintf (stderr,
822 "Failed to reinsert breakpoint at 0x%s (%s).\n",
823 paddress (bp->pc), strerror (err));
611cb4a5
DJ
824}
825
d50171e4
PA
826void
827reinsert_breakpoints_at (CORE_ADDR pc)
611cb4a5 828{
8b07ae33 829 struct raw_breakpoint *bp;
611cb4a5 830
8b07ae33 831 bp = find_raw_breakpoint_at (pc);
611cb4a5 832 if (bp == NULL)
611cb4a5 833 {
d50171e4
PA
834 /* This can happen when we remove all breakpoints while handling
835 a step-over. */
836 if (debug_threads)
837 fprintf (stderr,
8b07ae33 838 "Could not find raw breakpoint at 0x%s "
d50171e4
PA
839 "in list (reinserting).\n",
840 paddress (pc));
841 return;
611cb4a5
DJ
842 }
843
414a389f 844 reinsert_raw_breakpoint (bp);
d50171e4
PA
845}
846
0fb4aa4b
PA
847void
848reinsert_all_breakpoints (void)
849{
850 struct process_info *proc = current_process ();
851 struct raw_breakpoint *bp;
852
853 for (bp = proc->raw_breakpoints; bp != NULL; bp = bp->next)
854 if (!bp->inserted)
855 reinsert_raw_breakpoint (bp);
856}
857
d50171e4
PA
858void
859check_breakpoints (CORE_ADDR stop_pc)
860{
861 struct process_info *proc = current_process ();
862 struct breakpoint *bp, **bp_link;
863
864 bp = proc->breakpoints;
865 bp_link = &proc->breakpoints;
866
867 while (bp)
b65d95c5 868 {
8b07ae33 869 if (bp->raw->pc == stop_pc)
d50171e4 870 {
8b07ae33 871 if (!bp->raw->inserted)
d50171e4
PA
872 {
873 warning ("Hit a removed breakpoint?");
874 return;
875 }
876
877 if (bp->handler != NULL && (*bp->handler) (stop_pc))
878 {
879 *bp_link = bp->next;
880
8b07ae33 881 release_breakpoint (proc, bp);
d50171e4
PA
882
883 bp = *bp_link;
884 continue;
885 }
886 }
887
888 bp_link = &bp->next;
889 bp = *bp_link;
b65d95c5 890 }
611cb4a5
DJ
891}
892
893void
f450004a 894set_breakpoint_data (const unsigned char *bp_data, int bp_len)
611cb4a5
DJ
895{
896 breakpoint_data = bp_data;
897 breakpoint_len = bp_len;
898}
899
d50171e4
PA
900int
901breakpoint_here (CORE_ADDR addr)
902{
8b07ae33 903 return (find_raw_breakpoint_at (addr) != NULL);
d50171e4
PA
904}
905
906int
907breakpoint_inserted_here (CORE_ADDR addr)
908{
8b07ae33 909 struct raw_breakpoint *bp;
d50171e4 910
8b07ae33 911 bp = find_raw_breakpoint_at (addr);
d50171e4 912
8b07ae33 913 return (bp != NULL && bp->inserted);
d50171e4
PA
914}
915
d3bbe7a0
PA
916static int
917validate_inserted_breakpoint (struct raw_breakpoint *bp)
918{
919 unsigned char *buf;
920 int err;
921
922 gdb_assert (bp->inserted);
923
924 buf = alloca (breakpoint_len);
925 err = (*the_target->read_memory) (bp->pc, buf, breakpoint_len);
926 if (err || memcmp (buf, breakpoint_data, breakpoint_len) != 0)
927 {
928 /* Tag it as gone. */
929 bp->inserted = 0;
930 bp->shlib_disabled = 1;
931 return 0;
932 }
933
934 return 1;
935}
936
937static void
938delete_disabled_breakpoints (void)
939{
940 struct process_info *proc = current_process ();
941 struct breakpoint *bp, *next;
942
943 for (bp = proc->breakpoints; bp != NULL; bp = next)
944 {
945 next = bp->next;
946 if (bp->raw->shlib_disabled)
947 delete_breakpoint_1 (proc, bp);
948 }
949}
950
951/* Check if breakpoints we inserted still appear to be inserted. They
952 may disappear due to a shared library unload, and worse, a new
953 shared library may be reloaded at the same address as the
954 previously unloaded one. If that happens, we should make sure that
955 the shadow memory of the old breakpoints isn't used when reading or
956 writing memory. */
957
958void
959validate_breakpoints (void)
960{
961 struct process_info *proc = current_process ();
962 struct breakpoint *bp;
963
964 for (bp = proc->breakpoints; bp != NULL; bp = bp->next)
965 {
966 if (bp->raw->inserted)
967 validate_inserted_breakpoint (bp->raw);
968 }
969
970 delete_disabled_breakpoints ();
971}
972
611cb4a5 973void
f450004a 974check_mem_read (CORE_ADDR mem_addr, unsigned char *buf, int mem_len)
611cb4a5 975{
95954743 976 struct process_info *proc = current_process ();
8b07ae33 977 struct raw_breakpoint *bp = proc->raw_breakpoints;
fa593d66 978 struct fast_tracepoint_jump *jp = proc->fast_tracepoint_jumps;
611cb4a5 979 CORE_ADDR mem_end = mem_addr + mem_len;
d3bbe7a0 980 int disabled_one = 0;
611cb4a5 981
fa593d66
PA
982 for (; jp != NULL; jp = jp->next)
983 {
984 CORE_ADDR bp_end = jp->pc + jp->length;
985 CORE_ADDR start, end;
986 int copy_offset, copy_len, buf_offset;
987
6bf36717
JK
988 gdb_assert (fast_tracepoint_jump_shadow (jp) >= buf + mem_len
989 || buf >= fast_tracepoint_jump_shadow (jp) + (jp)->length);
990
fa593d66
PA
991 if (mem_addr >= bp_end)
992 continue;
993 if (jp->pc >= mem_end)
994 continue;
995
996 start = jp->pc;
997 if (mem_addr > start)
998 start = mem_addr;
999
1000 end = bp_end;
1001 if (end > mem_end)
1002 end = mem_end;
1003
1004 copy_len = end - start;
1005 copy_offset = start - jp->pc;
1006 buf_offset = start - mem_addr;
1007
1008 if (jp->inserted)
1009 memcpy (buf + buf_offset,
1010 fast_tracepoint_jump_shadow (jp) + copy_offset,
1011 copy_len);
1012 }
1013
611cb4a5
DJ
1014 for (; bp != NULL; bp = bp->next)
1015 {
1016 CORE_ADDR bp_end = bp->pc + breakpoint_len;
1017 CORE_ADDR start, end;
1018 int copy_offset, copy_len, buf_offset;
1019
6bf36717
JK
1020 gdb_assert (bp->old_data >= buf + mem_len
1021 || buf >= &bp->old_data[sizeof (bp->old_data)]);
1022
611cb4a5
DJ
1023 if (mem_addr >= bp_end)
1024 continue;
1025 if (bp->pc >= mem_end)
1026 continue;
1027
1028 start = bp->pc;
1029 if (mem_addr > start)
1030 start = mem_addr;
1031
1032 end = bp_end;
1033 if (end > mem_end)
1034 end = mem_end;
1035
1036 copy_len = end - start;
1037 copy_offset = start - bp->pc;
1038 buf_offset = start - mem_addr;
1039
8b07ae33 1040 if (bp->inserted)
d3bbe7a0
PA
1041 {
1042 if (validate_inserted_breakpoint (bp))
1043 memcpy (buf + buf_offset, bp->old_data + copy_offset, copy_len);
1044 else
1045 disabled_one = 1;
1046 }
611cb4a5 1047 }
d3bbe7a0
PA
1048
1049 if (disabled_one)
1050 delete_disabled_breakpoints ();
611cb4a5
DJ
1051}
1052
1053void
b9fd1791
PA
1054check_mem_write (CORE_ADDR mem_addr, unsigned char *buf,
1055 const unsigned char *myaddr, int mem_len)
611cb4a5 1056{
95954743 1057 struct process_info *proc = current_process ();
8b07ae33 1058 struct raw_breakpoint *bp = proc->raw_breakpoints;
fa593d66 1059 struct fast_tracepoint_jump *jp = proc->fast_tracepoint_jumps;
611cb4a5 1060 CORE_ADDR mem_end = mem_addr + mem_len;
d3bbe7a0 1061 int disabled_one = 0;
611cb4a5 1062
fa593d66
PA
1063 /* First fast tracepoint jumps, then breakpoint traps on top. */
1064
1065 for (; jp != NULL; jp = jp->next)
1066 {
1067 CORE_ADDR jp_end = jp->pc + jp->length;
1068 CORE_ADDR start, end;
1069 int copy_offset, copy_len, buf_offset;
1070
6bf36717
JK
1071 gdb_assert (fast_tracepoint_jump_shadow (jp) >= myaddr + mem_len
1072 || myaddr >= fast_tracepoint_jump_shadow (jp) + (jp)->length);
1073 gdb_assert (fast_tracepoint_jump_insn (jp) >= buf + mem_len
1074 || buf >= fast_tracepoint_jump_insn (jp) + (jp)->length);
1075
fa593d66
PA
1076 if (mem_addr >= jp_end)
1077 continue;
1078 if (jp->pc >= mem_end)
1079 continue;
1080
1081 start = jp->pc;
1082 if (mem_addr > start)
1083 start = mem_addr;
1084
1085 end = jp_end;
1086 if (end > mem_end)
1087 end = mem_end;
1088
1089 copy_len = end - start;
1090 copy_offset = start - jp->pc;
1091 buf_offset = start - mem_addr;
1092
1093 memcpy (fast_tracepoint_jump_shadow (jp) + copy_offset,
b9fd1791 1094 myaddr + buf_offset, copy_len);
fa593d66
PA
1095 if (jp->inserted)
1096 memcpy (buf + buf_offset,
1097 fast_tracepoint_jump_insn (jp) + copy_offset, copy_len);
1098 }
1099
611cb4a5
DJ
1100 for (; bp != NULL; bp = bp->next)
1101 {
1102 CORE_ADDR bp_end = bp->pc + breakpoint_len;
1103 CORE_ADDR start, end;
1104 int copy_offset, copy_len, buf_offset;
1105
6bf36717
JK
1106 gdb_assert (bp->old_data >= myaddr + mem_len
1107 || myaddr >= &bp->old_data[sizeof (bp->old_data)]);
1108
611cb4a5
DJ
1109 if (mem_addr >= bp_end)
1110 continue;
1111 if (bp->pc >= mem_end)
1112 continue;
1113
1114 start = bp->pc;
1115 if (mem_addr > start)
1116 start = mem_addr;
1117
1118 end = bp_end;
1119 if (end > mem_end)
1120 end = mem_end;
1121
1122 copy_len = end - start;
1123 copy_offset = start - bp->pc;
1124 buf_offset = start - mem_addr;
1125
b9fd1791 1126 memcpy (bp->old_data + copy_offset, myaddr + buf_offset, copy_len);
d50171e4 1127 if (bp->inserted)
d3bbe7a0
PA
1128 {
1129 if (validate_inserted_breakpoint (bp))
1130 memcpy (buf + buf_offset, breakpoint_data + copy_offset, copy_len);
1131 else
1132 disabled_one = 1;
1133 }
611cb4a5 1134 }
d3bbe7a0
PA
1135
1136 if (disabled_one)
1137 delete_disabled_breakpoints ();
611cb4a5 1138}
ae13219e 1139
95954743 1140/* Delete all breakpoints, and un-insert them from the inferior. */
ae13219e
DJ
1141
1142void
1143delete_all_breakpoints (void)
1144{
95954743
PA
1145 struct process_info *proc = current_process ();
1146
1147 while (proc->breakpoints)
8b07ae33 1148 delete_breakpoint_1 (proc, proc->breakpoints);
95954743
PA
1149}
1150
f9e39928 1151/* Clear the "inserted" flag in all breakpoints. */
95954743
PA
1152
1153void
f9e39928 1154mark_breakpoints_out (struct process_info *proc)
95954743 1155{
8b07ae33 1156 struct raw_breakpoint *raw_bp;
95954743 1157
8b07ae33
PA
1158 for (raw_bp = proc->raw_breakpoints; raw_bp != NULL; raw_bp = raw_bp->next)
1159 raw_bp->inserted = 0;
f9e39928
PA
1160}
1161
1162/* Release all breakpoints, but do not try to un-insert them from the
1163 inferior. */
1164
1165void
1166free_all_breakpoints (struct process_info *proc)
1167{
1168 mark_breakpoints_out (proc);
8b07ae33
PA
1169
1170 /* Note: use PROC explicitly instead of deferring to
1171 delete_all_breakpoints --- CURRENT_INFERIOR may already have been
1172 released when we get here. There should be no call to
1173 current_process from here on. */
95954743 1174 while (proc->breakpoints)
8b07ae33 1175 delete_breakpoint_1 (proc, proc->breakpoints);
ae13219e 1176}