binutils-gdb/gdb/dsrec.c
Ulrich Weigand 5af949e350 * defs.h (strlen_paddr, paddr, paddr_nz): Remove.
(paddress): Add GDBARCH parameter.
	* utils.c (strlen_paddr, paddr, paddr_nz): Remove.
	(paddress): Add GDBARCH parameter, use it instead of current_gdbarch.
	* ui-out.h (ui_out_field_core_addr): Add GDBARCH parameter.
	* ui-out.c (ui_out_field_core_addr): Add GDBARCH parameter,
	use it instead of current_gdbarch.

	Update calls to ui_out_field_core_addr to pass architecture:
	* ada-lang.c (print_one_exception): Update.
	* breakpoint.c (print_one_breakpoint_location,
	print_one_exception_catchpoint): Update.
	* disasm.c (dump_insns): Update.
	* darwin-nat-info.c (darwin_debug_regions_recurse): Update.
	* mi/mi-main.c (mi_cmd_data_read_memory): Update.
	* mi/mi-symbol-cmds.c: Include "objfiles.h".
	(mi_cmd_symbol_list_lines): Update.
	* stack.c (print_frame_info, print_frame): Update.

	Update callers of paddress to pass architecture:
	* ada-tasks.c (info_task): Update.
	* ada-valprint.c (ada_val_print_1): Update.
	* annotate.c (annotate_source, annotate_frame_begin): Update.
	* breakpoint.c (insert_bp_location, describe_other_breakpoints,
	mention): Update.
	* cli/cli-cmds.c (edit_command, list_command, print_disassembly):
	Update.
	* corefile.c (memory_error): Update.
	* c-valprint.c (print_function_pointer_address, c_val_print): Update.
	* disasm.c (dis_asm_print_address): Update.
	* exec.c (print_section_info): Update.
	* f-valprint.c (f_val_print): Update.
	* infcmd.c: Include "arch-utils.h".
	(jump_command, program_info): Update.
	* linux-fork.c: Include "arch-utils.h".
	(info_forks_command): Update.
	* m2-valprint.c (print_function_pointer_address,
	print_unpacked_pointer, print_variable_at_address,
	m2_val_print): Update.
	* m32r-rom.c (m32r_load_section, m32r_load, m32r_upload_command):
	Update.
	* printcmd.c (print_address, print_address_demangle, address_info):
	Update.
	* p-valprint.c (pascal_val_print): Update.
	* source.c: Include "arch-utils.h".
	(line_info): Update.
	* stack.c (frame_info, print_block_frame_labels): Update.
	* symfile.c (add_symbol_file_command, list_overlays_command): Update.
	* symmisc.c (dump_msymbols, dump_psymtab, dump_symtab_1,
	print_symbol, print_partial_symbols, maintenance_info_psymtabs,
	maintenance_check_symtabs): Update.
	* symtab.c (find_pc_sect_symtab): Update.
	* target.c (deprecated_debug_xfer_memory): Update.
	* tracepoint.c (scope_info): Update.
	* tui/tui-stack.c (tui_make_status_line): Update.
	* valprint.c (val_print_string): Update.

	Update callers of paddr_nz to use paddress instead (keeping
	user-visible output identical):
	* alpha-tdep.c (alpha_heuristic_proc_start): Update.
	* amd64-tdep.c (fixup_riprel, amd64_displaced_step_copy_insn,
	amd64_displaced_step_fixup): Update.
	* arch-utils.c (simple_displaced_step_copy_insn): Update.
	* auxv.c (fprint_target_auxv): Update.
	* breakpoint.c (insert_single_step_breakpoint): Update.
	* buildsym.c (finish_block): Update.
	* cli/cli-dump.c (restore_section_callback): Update.
	* fbsd-nat.c (fbsd_find_memory_regions): Update.
	* frame.c (frame_unwind_register_value): Update.
	* gcore.c (gcore_create_callback): Update.
	* hppa-tdep.c (hppa_frame_cache, hppa_skip_trampoline_code): Update.
	* i386-tdep.c (i386_displaced_step_fixup, i386_record_modrm,
	i386_record_lea_modrm_addr, i386_record_lea_modrm,
	i386_process_record): Update.
	* ia64-tdep.c (ia64_frame_this_id, ia64_sigtramp_frame_this_id,
	ia64_libunwind_frame_this_id, ia64_libunwind_sigtramp_frame_this_id,
	ia64_dummy_id, ia64_access_reg, ia64_access_rse_reg): Update.
	* infrun.c (displaced_step_prepare, displaced_step_fixup,
	handle_inferior_event, insert_step_resume_breakpoint_at_sal,
	insert_longjmp_resume_breakpoint): Update.
	* linux-nat.c (linux_nat_find_memory_regions): Update.
	* linux-record.c (record_linux_system_call): Update.
	* mips-tdep.c (heuristic_proc_start, mips_eabi_push_dummy_call,
	mips_n32n64_push_dummy_call, mips_o32_push_dummy_call,
	mips_o64_push_dummy_call): Update.
	* monitor.c (monitor_error, monitor_remove_breakpoint): Update.
	* record.c (record_arch_list_add_mem, record_wait,
	record_xfer_partial): Update.
	* remote-mips.c (mips_fetch_word, mips_check_lsi_error,
	mips_common_breakpoint): Update.
	* remote-sim.c (gdbsim_xfer_inferior_memory): Update.
	* rs6000-tdep.c (ppc_displaced_step_fixup): Update.
	* solib-som.c (som_current_sos): Update.
	* symfile.c (load_progress, generic_load): Update.
	* symfile-mem.c (add_vsyscall_page): Update.
	* valops.c (value_fetch_lazy): Update.
	* windows-tdep.c (windows_xfer_shared_library): Update.

	Update callers of paddr_nz to use paddress instead (changing
	user-visible output to make it more correct):
	* dwarf2loc.c (locexpr_describe_location): Update.
	* ia64-tdep.c (ia64_memory_insert_breakpoint,
	ia64_memory_remove_breakpoint): Update.
	* jv-valprint.c (java_value_print): Update.
	* m32c-tdep.c (m32c_m16c_address_to_pointer): Update.
	* monitor.c (monitor_read_memory): Update.

	Update callers of paddr to use paddress instead (changing
	user-visible output to make it more correct):
	* arm-tdep.c (arm_push_dummy_call): Update.
	* breakpoint.c (insert_bp_location, create_thread_event_breakpoint,
	create_breakpoint): Update.
	* darwin-nat-info.c (darwin_debug_regions): Update.
	* dcache.c (dcache_info): Update.
	* dsrec.c (load_srec, make_srec): Update.
	* dwarf2-frame.c (dwarf2_restore_rule, execute_cfa_program,
	dwarf2_frame_cache): Update.
	* gcore.c (gcore_copy_callback): Update.
	* gnu-nat.c (gnu_xfer_memory): Update.
	* mips-linux-nat.c (mips_show_dr): Update.
	* monitor.c (monitor_write_memory, monitor_insert_breakpoint,
	monitor_remove_breakpoint): Update.
	* remote.c (compare_sections_command): Update.
	* remote-m32r-sdi.c (m32r_xfer_memory, m32r_insert_breakpoint,
	m32r_remove_breakpoint, m32r_insert_watchpoint,
	m32r_remove_watchpoint): Update.
	* sol-thread.c (info_cb): Update.
	* symfile.c (load_progress): Update.

	Update callers of paddress or paddr_nz to use hex_string instead
	(changes output of internal/error/debug messages only):
	* dwarf2read.c (dump_die_shallow): Update.
	* frame.c (fprint_field, fprint_frame, frame_pc_unwind,
	get_frame_func, create_new_frame): Update.
	* hppa-tdep.c (find_unwind_entry, unwind_command): Update.
	* ia64-tdep.c (get_kernel_table, ia64_find_proc_info_x,
	ia64_get_dyn_info_list): Update.
	* maint.c (maintenance_translate_address): Update.
	* mi/mi-cmd-var.c (mi_cmd_var_create): Update.
	* target.c (target_flash_erase): Update.

	Update callers of paddr/paddr_nz to use phex/phex_nz instead,
	using an appropriate address size.  Remove use of strlen_paddr.
	* exec.c (exec_files_info): Update.
	* i386-nat.c (i386_show_dr): Update.
	* remote.c (remote_flash_erase): Update.
	* m32r-rom.c (m32r_load_section): Update.
	* monitor.c (monitor_vsprintf, monitor_store_register): Update.
	* remote.c (remote_check_symbols, remote_search_memory): Update.
	* remote-mips.c (mips_request, mips_common_breakpoint): Update.
	* scm-valprint.c (scm_ipruk, scm_scmval_print): Update.
	* sh64-tdep.c (sh64_show_media_regs, sh64_show_compact_regs): Update.
	* sh-tdep.c (sh_generic_show_regs, sh3_show_regs, sh2e_show_regs,
	sh2a_show_regs, sh2a_nofpu_show_regs, sh3e_show_regs,
	sh3_dsp_show_regs, sh4_show_regs, sh4_nofpu_show_regs,
	sh_dsp_show_regs): Update.
	* xcoffsolib.c (sharedlibrary_command): Update.


	* maint.c (maint_print_section_info): Add ADDR_SIZE parameter.
	Use hex_string_custom instead of paddr.
	(print_bfd_section_info): Pass address size.
	(print_objfile_section_info): Likewise.

	* annotate.h (annotate_source): Add GDBARCH parameter.
	(annotate_frame_begin): Likewise.
	* annotate.c (annotate_source): Add GDBARCH parameter.
	(annotate_frame_begin): Likewise.
	* source.c (identify_source_line): Update call to annotate_source.
	* stack.c (print_frame_info, print_frame): Update call to
	annotate_frame_begin.

	* breakpoint.c (describe_other_breakpoints): Add GDBARCH parameter.
	(create_breakpoint, create_ada_exception_breakpoint): Update call.

	* stack.c (print_block_frame_labels): Add GDBARCH parameter.
	(print_frame_label_vars): Update call.

	* symmisc.c (print_partial_symbols): Add GDBARCH parameter.
	(dump_psymtab): Update call to print_partial_symbols.
	(struct print_symbol_args): Add GDBARCH member.
	(dump_symtab_1): Set print_symbol_args architecture member.
	(print_symbol): Use it.

	* windows-tdep.h (windows_xfer_shared_library): Add GDBARCH
	parameter.
	* windows-tdep.c (windows_xfer_shared_library): Likewise.
	* i386-cygwin-tdep.c (struct cpms_data): Add GDBARCH member.
	(core_process_module_section): Pass architecture from cpms_data to
	windows_xfer_shared_library.
	(windows_core_xfer_shared_libraries): Initialize cmps_data
	architecture member.
	* windows-nat.c (windows_xfer_shared_libraries): Pass architecture
	to windows_xfer_shared_library.

	* defs.h (print_address): Add GDBARCH parameter.
	* printcmd.c (print_address): Add GDBARCH parameter.
	(print_scalar_formatted, do_examine): Update call.
	* findcmd.c (find_command): Update call.
	* tracepoint.c: Include "arch-utils.h".
	(trace_find_line_command): Update call.
	* tui/tui-disasm.c (tui_disassemble): Update call.

	* value.h (print_address_demangle): Add GDBARCH parameter.
	* printcmd.c (print_address_demangle): Add GDBARCH parameter.
	* c-valprint.c (print_function_pointer_address, c_val_print):
	Update call.
	* f-valprint.c (f_val_print): Update call.
	* gnu-v3-abi.c (gnuv3_print_method_ptr): Update call.
	* jv-valprint.c (java_val_print): Update call.
	* m2-valprint.c (print_function_pointer_address, m2_val_print):
	Update call.
	* p-valprint.c (pascal_val_print): Update call.

	* disasm.c (gdb_disassemble_info): Install architecture into
	di.application_data field.

testsuite/ChangeLog:

	* gdb.threads/tls-shared.exp: Update to locexpr_describe_location
	change to prefix TLS offset in hex with 0x.

doc/ChangeLog:

	* gdbint.texinfo (Item Output Functions): Update signature
	for ui_out_field_core_addr.
2009-07-02 17:21:10 +00:00

314 lines
9.3 KiB
C

/* S-record download support for GDB, the GNU debugger.
Copyright (C) 1995, 1996, 1997, 1999, 2000, 2001, 2003, 2004, 2007, 2008,
2009 Free Software Foundation, Inc.
This file is part of GDB.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>. */
#include "defs.h"
#include "serial.h"
#include "srec.h"
#include <time.h>
#include "gdb_assert.h"
#include "gdb_string.h"
extern void report_transfer_performance (unsigned long, time_t, time_t);
extern int remote_debug;
static int make_srec (char *srec, CORE_ADDR targ_addr, bfd * abfd,
asection * sect, int sectoff, int *maxrecsize,
int flags);
/* Download an executable by converting it to S records. DESC is a
`struct serial *' to send the data to. FILE is the name of the
file to be loaded. LOAD_OFFSET is the offset into memory to load
data into. It is usually specified by the user and is useful with
the a.out file format. MAXRECSIZE is the length in chars of the
largest S-record the host can accomodate. This is measured from
the starting `S' to the last char of the checksum. FLAGS is
various random flags, and HASHMARK is non-zero to cause a `#' to be
printed out for each record loaded. WAITACK, if non-NULL, is a
function that waits for an acknowledgement after each S-record, and
returns non-zero if the ack is read correctly. */
void
load_srec (struct serial *desc, const char *file, bfd_vma load_offset,
int maxrecsize,
int flags, int hashmark, int (*waitack) (void))
{
bfd *abfd;
asection *s;
char *srec;
int i;
int reclen;
time_t start_time, end_time;
unsigned long data_count = 0;
srec = (char *) alloca (maxrecsize + 1);
abfd = bfd_openr (file, 0);
if (!abfd)
{
printf_filtered (_("Unable to open file %s\n"), file);
return;
}
if (bfd_check_format (abfd, bfd_object) == 0)
{
printf_filtered (_("File is not an object file\n"));
return;
}
start_time = time (NULL);
/* Write a type 0 header record. no data for a type 0, and there
is no data, so len is 0. */
reclen = maxrecsize;
make_srec (srec, 0, NULL, (asection *) 1, 0, &reclen, flags);
if (remote_debug)
{
srec[reclen] = '\0';
puts_debug ("sent -->", srec, "<--");
}
serial_write (desc, srec, reclen);
for (s = abfd->sections; s; s = s->next)
if (s->flags & SEC_LOAD)
{
int numbytes;
bfd_vma addr = bfd_get_section_vma (abfd, s) + load_offset;
bfd_size_type size = bfd_get_section_size (s);
char *section_name = (char *) bfd_get_section_name (abfd, s);
/* Both GDB and BFD have mechanisms for printing addresses.
In the below, GDB's is used so that the address is
consistent with the rest of GDB. BFD's printf_vma() could
have also been used. cagney 1999-09-01 */
printf_filtered ("%s\t: %s .. %s ",
section_name,
paddress (target_gdbarch, addr),
paddress (target_gdbarch, addr + size));
gdb_flush (gdb_stdout);
data_count += size;
for (i = 0; i < size; i += numbytes)
{
reclen = maxrecsize;
numbytes = make_srec (srec, (CORE_ADDR) (addr + i), abfd, s,
i, &reclen, flags);
if (remote_debug)
{
srec[reclen] = '\0';
puts_debug ("sent -->", srec, "<--");
}
/* Repeatedly send the S-record until a good
acknowledgement is sent back. */
do
{
serial_write (desc, srec, reclen);
if (deprecated_ui_load_progress_hook)
if (deprecated_ui_load_progress_hook (section_name,
(unsigned long) i))
error (_("Canceled the download"));
}
while (waitack != NULL && !waitack ());
if (hashmark)
{
putchar_unfiltered ('#');
gdb_flush (gdb_stdout);
}
} /* Per-packet (or S-record) loop */
if (deprecated_ui_load_progress_hook)
if (deprecated_ui_load_progress_hook (section_name,
(unsigned long) i))
error (_("Canceled the download"));
putchar_unfiltered ('\n');
}
if (hashmark)
putchar_unfiltered ('\n');
end_time = time (NULL);
/* Write a terminator record. */
reclen = maxrecsize;
make_srec (srec, abfd->start_address, NULL, NULL, 0, &reclen, flags);
if (remote_debug)
{
srec[reclen] = '\0';
puts_debug ("sent -->", srec, "<--");
}
serial_write (desc, srec, reclen);
/* Some monitors need these to wake up properly. (Which ones? -sts) */
serial_write (desc, "\r\r", 2);
if (remote_debug)
puts_debug ("sent -->", "\r\r", "<---");
serial_flush_input (desc);
report_transfer_performance (data_count, start_time, end_time);
}
/*
* make_srec -- make an srecord. This writes each line, one at a
* time, each with it's own header and trailer line.
* An srecord looks like this:
*
* byte count-+ address
* start ---+ | | data +- checksum
* | | | |
* S01000006F6B692D746573742E73726563E4
* S315000448600000000000000000FC00005900000000E9
* S31A0004000023C1400037DE00F023604000377B009020825000348D
* S30B0004485A0000000000004E
* S70500040000F6
*
* S<type><length><address><data><checksum>
*
* Where
* - length
* is the number of bytes following upto the checksum. Note that
* this is not the number of chars following, since it takes two
* chars to represent a byte.
* - type
* is one of:
* 0) header record
* 1) two byte address data record
* 2) three byte address data record
* 3) four byte address data record
* 7) four byte address termination record
* 8) three byte address termination record
* 9) two byte address termination record
*
* - address
* is the start address of the data following, or in the case of
* a termination record, the start address of the image
* - data
* is the data.
* - checksum
* is the sum of all the raw byte data in the record, from the length
* upwards, modulo 256 and subtracted from 255.
*
* This routine returns the length of the S-record.
*
*/
static int
make_srec (char *srec, CORE_ADDR targ_addr, bfd *abfd, asection *sect,
int sectoff, int *maxrecsize, int flags)
{
unsigned char checksum;
int tmp;
const static char hextab[] = "0123456789ABCDEF";
const static char data_code_table[] = "123";
const static char term_code_table[] = "987";
const static char header_code_table[] = "000";
char const *code_table;
int addr_size;
int payload_size;
char *binbuf;
char *p;
if (sect)
{
tmp = flags; /* Data or header record */
code_table = abfd ? data_code_table : header_code_table;
binbuf = alloca (*maxrecsize / 2);
}
else
{
tmp = flags >> SREC_TERM_SHIFT; /* Term record */
code_table = term_code_table;
binbuf = NULL;
}
if ((tmp & SREC_2_BYTE_ADDR) && (targ_addr <= 0xffff))
addr_size = 2;
else if ((tmp & SREC_3_BYTE_ADDR) && (targ_addr <= 0xffffff))
addr_size = 3;
else if (tmp & SREC_4_BYTE_ADDR)
addr_size = 4;
else
internal_error (__FILE__, __LINE__,
_("make_srec: Bad address (%s), or bad flags (0x%x)."),
paddress (target_gdbarch, targ_addr), flags);
/* Now that we know the address size, we can figure out how much
data this record can hold. */
if (sect && abfd)
{
payload_size = (*maxrecsize - (1 + 1 + 2 + addr_size * 2 + 2)) / 2;
payload_size = min (payload_size, bfd_get_section_size (sect) - sectoff);
bfd_get_section_contents (abfd, sect, binbuf, sectoff, payload_size);
}
else
payload_size = 0; /* Term or header packets have no payload */
/* Output the header. */
snprintf (srec, (*maxrecsize) + 1, "S%c%02X%0*X",
code_table[addr_size - 2],
addr_size + payload_size + 1,
addr_size * 2, (int) targ_addr);
/* Note that the checksum is calculated on the raw data, not the
hexified data. It includes the length, address and the data
portions of the packet. */
checksum = 0;
checksum += (payload_size + addr_size + 1 /* Packet length */
+ (targ_addr & 0xff) /* Address... */
+ ((targ_addr >> 8) & 0xff)
+ ((targ_addr >> 16) & 0xff)
+ ((targ_addr >> 24) & 0xff));
/* NOTE: cagney/2003-08-10: The equation is old. Check that the
recent snprintf changes match that equation. */
gdb_assert (strlen (srec) == 1 + 1 + 2 + addr_size * 2);
p = srec + 1 + 1 + 2 + addr_size * 2;
/* Build the Srecord. */
for (tmp = 0; tmp < payload_size; tmp++)
{
unsigned char k;
k = binbuf[tmp];
*p++ = hextab[k >> 4];
*p++ = hextab[k & 0xf];
checksum += k;
}
checksum = ~checksum;
*p++ = hextab[checksum >> 4];
*p++ = hextab[checksum & 0xf];
*p++ = '\r';
*maxrecsize = p - srec;
return payload_size;
}