/************************************************************* * File: imon/load.c * Purpose: file load command for imon * Author: Phil Bunce (pjb@carmel.com) * Revision History: * 970303 Deleted unused static globals * 970303 Moved def of blksz and blkinx here. * 970305 Added -f flag to load from flash * 970305 Deleted -t from _opts. It isn't implemented anyway. * 970305 delete all line termination characters. * 970514 Add null to eol deletion list - needed for Ethernet * 970901 Removed lastdownloadsz. See getNextSloadAdr(). * 970902 Prob w "goto drvrInit" in "load -f". Created callDriver(). * 970920 Added error msg if "load -f" w/o reset. * 980107 Added ifdef for GHS jal indirect bug * 980113 Added (char *) casts for av[] * 980206 Move cache flush to start of 'callDriver'. * 980405 Added -m option. * 980602 Added len check for driver loads. */ #include #include Optdesc load_opts[] = { {"[-vbeasi][-baud][offset][-c cmdstr]","load memory from hostport"}, {"-c cmdstr","send cmdstr to host"}, {"-s","don't clear symbols"}, {"-b","don't clear breakpoints"}, {"-e","don't clear exception handlers"}, {"-a","don't add offset to symbols"}, {"-d","load Target Description Driver"}, /* {"-t","load at top of memory"}, 970305 */ {"-f","load driver from flash"}, {"-i","ignore checksum errors"}, #ifdef ETHERNET {"-B","binary transfer mode"}, {"-v","verbose mode"}, #endif {"-","set baud rate"}, {"-m","don't load memory - symbols only"}, {0}}; char *dlerrs[] = {0,"bad char","bad length","bad type", "bad chksum", "out of symbol space"}; #ifdef CROSSVIEW #ifdef NOPROTO #define _(x) () #else #define _(x) x #endif #define REC_END 2 #define REC_DATA 3 #define REC_ERROR 4 typedef unsigned long ADDR; #endif Ulong start_address; Ulong nextaddr; Ulong wordbuf; Ulong tbase; int chksum; int tot; int blksz; int blkinx; #define ether_bcopy() (* ether_bcopy_ptr)() Func *ether_bcopy_ptr; /************************************************************* * load(ac,av) */ load(ac,av) int ac; Uchar *av[]; { struct termio tbuf; char *hostport,*cmdstr,*p; int fd,dlecho,dlproto,dltype,count,n; int len,err,i,j,s,flags; Ulong offset; Uchar recbuf[MAXREC],*baudrate; int errs[6],line; int fflag; U64 rv; baudrate = 0; offset = 0; count = 0; cmdstr = 0; flags = 0; for (i=0;i<6;i++) errs[i] = 0; hostport = getMonEnv("hostport"); vflag = fflag = 0; for (i=1;i= ac) { printf("bad arg count\n"); return(1); } cmdstr = (char *)av[i]; /* 980113 */ break; } else if (isdigit(av[i][j])) { baudrate = &av[i][j]; break; } else printf("%c: unrecognized option\n",av[i][j]); } } else { if (av[i][0] == 't') hostport = (char *)av[i]; /* 980113 */ else if (count == 0) { if (!get_rsa(&rv,av[i])) return(1); offset = rv.lo; count++; } else printf("%s: unrecognized argument\n",av[i]); } } if (regChain && fflag) { /* 970920 */ printf("ERROR: reset controller before reloading driver.\n"); return; } if (!(flags&DL_SFLAG)) clrsyms(); if (!(flags&DL_bFLAG)) clrbpt(-1); if (!(flags&DL_EFLAG)) clrhndlrs(); if (fflag) { /* load from flash */ int val,len; Ulong src,dst; src = nvInfo.dvrsa; dst = DRIVER_BASE; /* len always stored in BE format */ len = load_byte(src++); len = (len<<8)|load_byte(src++); len = (len<<8)|load_byte(src++); len = (len<<8)|load_byte(src++); if (len == -1 || len > 0x20000) { /* 980602 */ printf("driver not found.\n"); return; } printf("loading %d bytes to %08x\n",len,dst); for (i=0;i 0) writec(fd,CNTRL('u')); else writec(fd,CNTRL('f')); } } if (dlecho == LFEED) writec(fd,'\n'); if (fd > STDERR) close(fd); flush_target(ICACHE); if (err) { printf("\n%d errors\n",err); for (i=1;i<6;i++) if (errs[i]) printf(" %3d %s\n",errs[i],dlerrs[i]); } else { if ( dltype == 2 ) printf("!540!pc=%08x\n", start_address ); else { if (!(flags&DL_DFLAG)) printf("Entry address is %08x\n",getPc()); printf("\ntotal = 0x%x bytes\n",tot); } } writec(fd,CNTRL('q')); if (!err && flags&DL_DFLAG) callDriver(); } /************************************************************* * callDriver() */ callDriver() { DriverTbl *d; Func *f; flush_cache(DCACHE); flush_cache(ICACHE); d = (DriverTbl *)DRIVER_BASE; if (d->version != DVRIF_VERS) { printf("%d: unexpected driver interface version. Need %d\n", d->version,DVRIF_VERS); if (d->version > 10000) { printf("It looks like it might have the wrong endianness\n"); } return; } cpuType = *d->cputype; printf("%s has been loaded.\n",d->name); addGpRegs(); #ifdef GHS f = (Func *)DRIVER_BASE; (* f)(); /* call the driver */ #else (* ((Func *)DRIVER_BASE))(); /* call the driver */ #endif }