X-Git-Url: http://drtracing.org/?a=blobdiff_plain;f=gdb%2Fremote-nindy.c;h=f9cac2bad2681ccb6bf17c20fe4f5fb9550c5bce;hb=c20c1bdf992a90db69c4abb73594b2ff58154ef6;hp=c168511be7c40613441b70083768100773629748;hpb=6ecb870e368f88cacd94e570308edcc6f8e50458;p=deliverable%2Fbinutils-gdb.git diff --git a/gdb/remote-nindy.c b/gdb/remote-nindy.c index c168511be7..f9cac2bad2 100644 --- a/gdb/remote-nindy.c +++ b/gdb/remote-nindy.c @@ -116,6 +116,11 @@ NINDY ROM monitor at the other end of the line. #include "nindy-share/env.h" #include "nindy-share/stop.h" +#include "dcache.h" +#include "remote-utils.h" + +static DCACHE *nindy_dcache; + extern int unlink(); extern char *getenv(); extern char *mktemp(); @@ -123,10 +128,12 @@ extern char *mktemp(); extern void generic_mourn_inferior (); extern struct target_ops nindy_ops; -extern FILE *instream; +extern GDB_FILE *instream; extern struct ext_format ext_format_i960; /* i960-tdep.c */ extern char ninStopWhy (); +extern int ninMemGet (); +extern int ninMemPut (); int nindy_initial_brk; /* nonzero if want to send an initial BREAK to nindy */ int nindy_old_protocol; /* nonzero if want to use old protocol */ @@ -145,12 +152,6 @@ static int regs_changed = 0; /* 1 iff regs were modified since last read */ extern char *exists(); -static void -dcache_flush (), dcache_poke (), dcache_init(); - -static int -dcache_fetch (); - static void nindy_fetch_registers PARAMS ((int)); @@ -173,29 +174,34 @@ nindy_close (quitting) } /* Open a connection to a remote debugger. - FIXME, there should be a way to specify the various options that are - now specified with gdb command-line options. (baud_rate, old_protocol, - and initial_brk) */ + FIXME, there should be "set" commands for the options that are + now specified with gdb command-line options (old_protocol, + and initial_brk). */ void nindy_open (name, from_tty) char *name; /* "/dev/ttyXX", "ttyXX", or "XX": tty to be opened */ int from_tty; { + char baudrate[1024]; if (!name) error_no_arg ("serial port device name"); target_preopen (from_tty); - + nindy_close (0); have_regs = regs_changed = 0; - dcache_init(); + nindy_dcache = dcache_init(ninMemGet, ninMemPut); /* Allow user to interrupt the following -- we could hang if there's no NINDY at the other end of the remote tty. */ immediate_quit++; - ninConnect(name, baud_rate ? baud_rate : "9600", + /* If baud_rate is -1, then ninConnect will not recognize the baud rate + and will deal with the situation in a (more or less) reasonable + fashion. */ + sprintf(baudrate, "%d", baud_rate); + ninConnect(name, baudrate, nindy_initial_brk, !from_tty, nindy_old_protocol); immediate_quit--; @@ -224,8 +230,9 @@ nindy_detach (name, from_tty) static void nindy_files_info () { - printf("\tAttached to %s at %s bps%s%s.\n", savename, - baud_rate? baud_rate: "9600", + /* FIXME: this lies about the baud rate if we autobauded. */ + printf_unfiltered("\tAttached to %s at %d bits per second%s%s.\n", savename, + baud_rate, nindy_old_protocol? " in old protocol": "", nindy_initial_brk? " with initial break": ""); } @@ -253,12 +260,13 @@ non_dle( buf, n ) void nindy_resume (pid, step, siggnal) - int pid, step, siggnal; + int pid, step; + enum target_signal siggnal; { - if (siggnal != 0 && siggnal != stop_signal) - error ("Can't send signals to remote NINDY targets."); + if (siggnal != TARGET_SIGNAL_0 && siggnal != stop_signal) + warning ("Can't send signals to remote NINDY targets."); - dcache_flush(); + dcache_flush(nindy_dcache); if ( regs_changed ){ nindy_store_registers (-1); regs_changed = 0; @@ -289,15 +297,16 @@ You may need to reset the 80960 and/or reload your program.\n"); } /* Wait until the remote machine stops. While waiting, operate in passthrough - * mode; i.e., pass everything NINDY sends to stdout, and everything from + * mode; i.e., pass everything NINDY sends to gdb_stdout, and everything from * stdin to NINDY. * * Return to caller, storing status in 'status' just as `wait' would. */ static int -nindy_wait( status ) - WAITTYPE *status; +nindy_wait( pid, status ) + int pid; + struct target_waitstatus *status; { fd_set fds; char buf[500]; /* FIXME, what is "500" here? */ @@ -308,7 +317,8 @@ nindy_wait( status ) struct cleanup *old_cleanups; long ip_value, fp_value, sp_value; /* Reg values from stop */ - WSETEXIT( (*status), 0 ); + status->kind = TARGET_WAITKIND_EXITED; + status->value.integer = 0; /* OPERATE IN PASSTHROUGH MODE UNTIL NINDY SENDS A DLE CHARACTER */ @@ -387,30 +397,13 @@ nindy_wait( status ) if (stop_exit) { - /* User program exited */ - WSETEXIT ((*status), stop_code); + status->kind = TARGET_WAITKIND_EXITED; + status->value.integer = stop_code; } else { - /* Fault or trace */ - switch (stop_code) - { - case STOP_GDB_BPT: - case TRACE_STEP: - /* Breakpoint or single stepping. */ - stop_code = SIGTRAP; - break; - default: - /* The target is not running Unix, and its faults/traces do - not map nicely into Unix signals. Make sure they do not - get confused with Unix signals by numbering them with - values higher than the highest legal Unix signal. code - in i960_print_fault(), called via PRINT_RANDOM_SIGNAL, - will interpret the value. */ - stop_code += NSIG; - break; - } - WSETSTOP ((*status), stop_code); + status->kind = TARGET_WAITKIND_STOPPED; + status->value.sig = i960_fault_to_signal (stop_code); } return inferior_pid; } @@ -468,7 +461,7 @@ nindy_store_registers(regno) int regno; { struct nindy_regs nindy_regs; - int regnum, inv; + int regnum; double dub; memcpy (nindy_regs.local_regs, ®isters[REGISTER_BYTE (R0_REGNUM)], 16*4); @@ -476,18 +469,14 @@ nindy_store_registers(regno) memcpy (nindy_regs.pcw_acw, ®isters[REGISTER_BYTE (PCW_REGNUM)], 2*4); memcpy (nindy_regs.ip, ®isters[REGISTER_BYTE (IP_REGNUM)], 1*4); memcpy (nindy_regs.tcw, ®isters[REGISTER_BYTE (TCW_REGNUM)], 1*4); - /* Float regs. Only works on IEEE_FLOAT hosts. FIXME! */ - for (regnum = FP0_REGNUM; regnum < FP0_REGNUM + 4; regnum++) { - ieee_extended_to_double (&ext_format_i960, - ®isters[REGISTER_BYTE (regnum)], &dub); - /* dub now in host byte order */ - /* FIXME-someday, the arguments to unpack_double are backward. - It expects a target double and returns a host; we pass the opposite. - This mostly works but not quite. */ - dub = unpack_double (builtin_type_double, (char *)&dub, &inv); - /* dub now in target byte order */ - memcpy (&nindy_regs.fp_as_double[8 * (regnum - FP0_REGNUM)], &dub, 8); - } + for (regnum = FP0_REGNUM; regnum < FP0_REGNUM + 4; regnum++) + { + ieee_extended_to_double (&ext_format_i960, + ®isters[REGISTER_BYTE (regnum)], &dub); + store_floating (&nindy_regs.fp_as_double[8 * (regnum - FP0_REGNUM)], + REGISTER_VIRTUAL_SIZE (regnum), + dub); + } immediate_quit++; ninRegsPut( (char *) &nindy_regs ); @@ -501,7 +490,7 @@ int nindy_fetch_word (addr) CORE_ADDR addr; { - return dcache_fetch (addr); + return dcache_fetch (nindy_dcache, addr); } /* Write a word WORD into remote address ADDR. @@ -512,7 +501,7 @@ nindy_store_word (addr, word) CORE_ADDR addr; int word; { - dcache_poke (addr, word); + dcache_poke (nindy_dcache, addr, word); } /* Copy LEN bytes to or from inferior's memory starting at MEMADDR @@ -587,170 +576,6 @@ nindy_xfer_inferior_memory(memaddr, myaddr, len, write, target) return len; } -/* The data cache records all the data read from the remote machine - since the last time it stopped. - - Each cache block holds 16 bytes of data - starting at a multiple-of-16 address. */ - -#define DCACHE_SIZE 64 /* Number of cache blocks */ - -struct dcache_block { - struct dcache_block *next, *last; - unsigned int addr; /* Address for which data is recorded. */ - int data[4]; -}; - -struct dcache_block dcache_free, dcache_valid; - -/* Free all the data cache blocks, thus discarding all cached data. */ -static -void -dcache_flush () -{ - register struct dcache_block *db; - - while ((db = dcache_valid.next) != &dcache_valid) - { - remque (db); - insque (db, &dcache_free); - } -} - -/* - * If addr is present in the dcache, return the address of the block - * containing it. - */ -static -struct dcache_block * -dcache_hit (addr) - unsigned int addr; -{ - register struct dcache_block *db; - - if (addr & 3) - abort (); - - /* Search all cache blocks for one that is at this address. */ - db = dcache_valid.next; - while (db != &dcache_valid) - { - if ((addr & 0xfffffff0) == db->addr) - return db; - db = db->next; - } - return NULL; -} - -/* Return the int data at address ADDR in dcache block DC. */ -static -int -dcache_value (db, addr) - struct dcache_block *db; - unsigned int addr; -{ - if (addr & 3) - abort (); - return (db->data[(addr>>2)&3]); -} - -/* Get a free cache block, put or keep it on the valid list, - and return its address. The caller should store into the block - the address and data that it describes, then remque it from the - free list and insert it into the valid list. This procedure - prevents errors from creeping in if a ninMemGet is interrupted - (which used to put garbage blocks in the valid list...). */ -static -struct dcache_block * -dcache_alloc () -{ - register struct dcache_block *db; - - if ((db = dcache_free.next) == &dcache_free) - { - /* If we can't get one from the free list, take last valid and put - it on the free list. */ - db = dcache_valid.last; - remque (db); - insque (db, &dcache_free); - } - - remque (db); - insque (db, &dcache_valid); - return (db); -} - -/* Return the contents of the word at address ADDR in the remote machine, - using the data cache. */ -static -int -dcache_fetch (addr) - CORE_ADDR addr; -{ - register struct dcache_block *db; - - db = dcache_hit (addr); - if (db == 0) - { - db = dcache_alloc (); - immediate_quit++; - ninMemGet(addr & ~0xf, (unsigned char *)db->data, 16); - immediate_quit--; - db->addr = addr & ~0xf; - remque (db); /* Off the free list */ - insque (db, &dcache_valid); /* On the valid list */ - } - return (dcache_value (db, addr)); -} - -/* Write the word at ADDR both in the data cache and in the remote machine. */ -static void -dcache_poke (addr, data) - CORE_ADDR addr; - int data; -{ - register struct dcache_block *db; - - /* First make sure the word is IN the cache. DB is its cache block. */ - db = dcache_hit (addr); - if (db == 0) - { - db = dcache_alloc (); - immediate_quit++; - ninMemGet(addr & ~0xf, (unsigned char *)db->data, 16); - immediate_quit--; - db->addr = addr & ~0xf; - remque (db); /* Off the free list */ - insque (db, &dcache_valid); /* On the valid list */ - } - - /* Modify the word in the cache. */ - db->data[(addr>>2)&3] = data; - - /* Send the changed word. */ - immediate_quit++; - ninMemPut(addr, (unsigned char *)&data, 4); - immediate_quit--; -} - -/* The cache itself. */ -struct dcache_block the_cache[DCACHE_SIZE]; - -/* Initialize the data cache. */ -static void -dcache_init () -{ - register i; - register struct dcache_block *db; - - db = the_cache; - dcache_free.next = dcache_free.last = &dcache_free; - dcache_valid.next = dcache_valid.last = &dcache_valid; - for (i=0;i