struct breakpoint *b;
if (memory_breakpoint_size < 0)
- /* No breakpoints on this machine. */
+ /* No breakpoints on this machine. FIXME: This should be
+ dependent on the debugging target. Probably want
+ target_insert_breakpoint to return a size, saying how many
+ bytes of the shadow contents are used, or perhaps have
+ something like target_xfer_shadow. */
return target_read_memory (memaddr, myaddr, len);
ALL_BREAKPOINTS (b)
{
bpstat p = NULL;
bpstat tmp;
- bpstat retval;
+ bpstat retval = NULL;
if (bs == NULL)
return bs;
bs->stop = 0;
else
{
- int value_is_zero;
+ int value_is_zero = 0;
if (b->cond)
{
for (; bs != NULL; bs = bs->next)
{
- enum class bs_class;
+ enum class bs_class = no_effect;
if (bs->breakpoint_at == NULL)
/* I suspect this can happen if it was a momentary breakpoint
which has since been deleted. */
static char bpenables[] = "ny";
char wrap_indent[80];
- if (!breakpoint_chain)
- {
- printf_filtered ("No breakpoints or watchpoints.\n");
- return;
- }
-
ALL_BREAKPOINTS (b)
if (bnum == -1
|| bnum == b->number)
printf_filtered ("%s ", local_hex_string_custom(b->address, "08"));
last_addr = b->address;
- if (b->symtab)
+ if (b->source_file)
{
sym = find_pc_function (b->address);
if (sym)
wrap_here (wrap_indent);
fputs_filtered (" at ", stdout);
}
- fputs_filtered (b->symtab->filename, stdout);
+ fputs_filtered (b->source_file, stdout);
printf_filtered (":%d", b->line_number);
}
else
print_address_symbolic (b->address, stdout, demangle, " ");
+ /* intentional fall-through */
+ case bp_step_resume: /* do nothing. */
+ break;
}
printf_filtered ("\n");
}
}
- if (!found_a_breakpoint
- && bnum != -1)
- printf_filtered ("No breakpoint or watchpoint number %d.\n", bnum);
+ if (!found_a_breakpoint)
+ {
+ if (bnum == -1)
+ printf_filtered ("No breakpoints or watchpoints.\n");
+ else
+ printf_filtered ("No breakpoint or watchpoint number %d.\n", bnum);
+ }
else
/* Compare against (CORE_ADDR)-1 in case some compiler decides
that a comparison of an unsigned with -1 is always false. */
b = (struct breakpoint *) xmalloc (sizeof (struct breakpoint));
memset (b, 0, sizeof (*b));
b->address = sal.pc;
- b->symtab = sal.symtab;
+ if (sal.symtab == NULL)
+ b->source_file = NULL;
+ else
+ b->source_file = savestring (sal.symtab->filename,
+ strlen (sal.symtab->filename));
b->line_number = sal.line;
b->enable = enabled;
b->next = 0;
case bp_breakpoint:
printf_filtered ("Breakpoint %d at %s", b->number,
local_hex_string(b->address));
- if (b->symtab)
+ if (b->source_file)
printf_filtered (": file %s, line %d.",
- b->symtab->filename, b->line_number);
+ b->source_file, b->line_number);
break;
case bp_until:
case bp_finish:
case bp_longjmp:
case bp_longjmp_resume:
+ case bp_step_resume:
break;
}
printf_filtered ("\n");
/* Pointers in arg to the start, and one past the end, of the condition. */
char *cond_start = NULL;
- char *cond_end;
+ char *cond_end = NULL;
/* Pointers in arg to the start, and one past the end,
of the address part. */
char *addr_start = NULL;
- char *addr_end;
+ char *addr_end = NULL;
+ struct cleanup *old_chain;
+ struct cleanup *canonical_strings_chain = NULL;
+ char **canonical = (char **)NULL;
int i;
&& (!current_source_symtab
|| (arg && (*arg == '+' || *arg == '-'))))
sals = decode_line_1 (&arg, 1, default_breakpoint_symtab,
- default_breakpoint_line);
+ default_breakpoint_line, &canonical);
else
- sals = decode_line_1 (&arg, 1, (struct symtab *)NULL, 0);
+ sals = decode_line_1 (&arg, 1, (struct symtab *)NULL, 0, &canonical);
addr_end = arg;
}
if (! sals.nelts)
return;
+ /* Make sure that all storage allocated in decode_line_1 gets freed in case
+ the following `for' loop errors out. */
+ old_chain = make_cleanup (free, sals.sals);
+ if (canonical != (char **)NULL)
+ {
+ make_cleanup (free, canonical);
+ canonical_strings_chain = make_cleanup (null_cleanup, 0);
+ for (i = 0; i < sals.nelts; i++)
+ {
+ if (canonical[i] != NULL)
+ make_cleanup (free, canonical[i]);
+ }
+ }
+
/* Resolve all line numbers to PC's, and verify that conditions
can be parsed, before setting any breakpoints. */
for (i = 0; i < sals.nelts; i++)
}
}
+ /* Remove the canonical strings from the cleanup, they are needed below. */
+ if (canonical != (char **)NULL)
+ discard_cleanups (canonical_strings_chain);
+
/* Now set all the breakpoints. */
for (i = 0; i < sals.nelts; i++)
{
b->type = bp_breakpoint;
b->cond = cond;
- /* FIXME: We should add the filename if this is a static function
- and probably if it is a line number (the line numbers could
- have changed when we re-read symbols; possibly better to disable
- the breakpoint in that case). */
- if (addr_start)
+ /* If a canonical line spec is needed use that instead of the
+ command string. */
+ if (canonical != (char **)NULL && canonical[i] != NULL)
+ b->addr_string = canonical[i];
+ else if (addr_start)
b->addr_string = savestring (addr_start, addr_end - addr_start);
if (cond_start)
b->cond_string = savestring (cond_start, cond_end - cond_start);
printf ("Multiple breakpoints were set.\n");
printf ("Use the \"delete\" command to delete unwanted breakpoints.\n");
}
- free ((PTR)sals.sals);
+ do_cleanups (old_chain);
}
/* Helper function for break_command_1 and disassemble_command. */
if (default_breakpoint_valid)
sals = decode_line_1 (&arg, 1, default_breakpoint_symtab,
- default_breakpoint_line);
+ default_breakpoint_line, (char ***)NULL);
else
- sals = decode_line_1 (&arg, 1, (struct symtab *)NULL, 0);
+ sals = decode_line_1 (&arg, 1, (struct symtab *)NULL, 0, (char ***)NULL);
if (sals.nelts != 1)
error ("Couldn't get information on specified line.");
b->enable = enabled;
b->disposition = tempflag ? delete : donttouch;
- printf ("Breakpoint %d at %s", b->number, local_hex_string(b->address));
- if (b->symtab)
- printf (": file %s, line %d.", b->symtab->filename, b->line_number);
- printf ("\n");
+ mention (b);
}
if (sals.nelts > 1)
sal = sals.sals[i];
found = (struct breakpoint *) 0;
while (breakpoint_chain
- && (sal.pc ? breakpoint_chain->address == sal.pc
- : (breakpoint_chain->symtab == sal.symtab
+ && (sal.pc
+ ? breakpoint_chain->address == sal.pc
+ : (breakpoint_chain->source_file != NULL
+ && sal.symtab != NULL
+ && STREQ (breakpoint_chain->source_file,
+ sal.symtab->filename)
&& breakpoint_chain->line_number == sal.line)))
{
b1 = breakpoint_chain;
ALL_BREAKPOINTS (b)
while (b->next
&& b->next->type != bp_watchpoint
- && (sal.pc ? b->next->address == sal.pc
- : (b->next->symtab == sal.symtab
+ && (sal.pc
+ ? b->next->address == sal.pc
+ : (b->next->source_file != NULL
+ && sal.symtab != NULL
+ && STREQ (b->next->source_file, sal.symtab->filename)
&& b->next->line_number == sal.line)))
{
b1 = b->next;
free_command_lines (&bpt->commands);
if (bpt->cond)
- free ((PTR)bpt->cond);
+ free (bpt->cond);
if (bpt->cond_string != NULL)
- free ((PTR)bpt->cond_string);
+ free (bpt->cond_string);
if (bpt->addr_string != NULL)
- free ((PTR)bpt->addr_string);
+ free (bpt->addr_string);
if (bpt->exp_string != NULL)
- free ((PTR)bpt->exp_string);
+ free (bpt->exp_string);
+ if (bpt->source_file != NULL)
+ free (bpt->source_file);
if (xgdb_verbose && bpt->type == bp_breakpoint)
printf ("breakpoint #%d deleted\n", bpt->number);
b->enable = disabled;
s = b->addr_string;
- sals = decode_line_1 (&s, 1, (struct symtab *)NULL, 0);
+ sals = decode_line_1 (&s, 1, (struct symtab *)NULL, 0, (char ***)NULL);
for (i = 0; i < sals.nelts; i++)
{
resolve_sal_pc (&sals.sals[i]);
- if (b->symtab != sals.sals[i].symtab
- || b->line_number != sals.sals[i].line
- || b->address != sals.sals[i].pc)
+
+ /* Reparse conditions, they might contain references to the
+ old symtab. */
+ if (b->cond_string != NULL)
{
- b->symtab = sals.sals[i].symtab;
+ s = b->cond_string;
+ if (b->cond)
+ free ((PTR)b->cond);
+ b->cond = parse_exp_1 (&s, block_for_pc (sals.sals[i].pc), 0);
+ }
+
+ /* We need to re-set the breakpoint if the address changes...*/
+ if (b->address != sals.sals[i].pc
+ /* ...or new and old breakpoints both have source files, and
+ the source file name or the line number changes... */
+ || (b->source_file != NULL
+ && sals.sals[i].symtab != NULL
+ && (!STREQ (b->source_file, sals.sals[i].symtab->filename)
+ || b->line_number != sals.sals[i].line)
+ )
+ /* ...or we switch between having a source file and not having
+ one. */
+ || ((b->source_file == NULL) != (sals.sals[i].symtab == NULL))
+ )
+ {
+ if (b->source_file != NULL)
+ free (b->source_file);
+ if (sals.sals[i].symtab == NULL)
+ b->source_file = NULL;
+ else
+ b->source_file =
+ savestring (sals.sals[i].symtab->filename,
+ strlen (sals.sals[i].symtab->filename));
b->line_number = sals.sals[i].line;
b->address = sals.sals[i].pc;
-
- if (b->cond_string != NULL)
- {
- s = b->cond_string;
- if (b->cond)
- free ((PTR)b->cond);
- b->cond = parse_exp_1 (&s, block_for_pc (sals.sals[i].pc), 0);
- }
check_duplicates (b->address);
enable_breakpoint (bpt)
struct breakpoint *bpt;
{
- FRAME save_selected_frame;
+ FRAME save_selected_frame = NULL;
int save_selected_frame_level = -1;
bpt->enable = enabled;
error ("Empty line specification.");
if (default_breakpoint_valid)
sals = decode_line_1 (&string, funfirstline,
- default_breakpoint_symtab, default_breakpoint_line);
+ default_breakpoint_symtab, default_breakpoint_line,
+ (char ***)NULL);
else
- sals = decode_line_1 (&string, funfirstline, (struct symtab *)NULL, 0);
+ sals = decode_line_1 (&string, funfirstline,
+ (struct symtab *)NULL, 0, (char ***)NULL);
if (*string)
error ("Junk at end of line specification: %s", string);
return sals;