void IRQ_Routine (void) __attribute__ ((interrupt("IRQ"))); void FIQ_Routine (void) __attribute__ ((interrupt("FIQ"))); void SWI_Routine (void) __attribute__ ((interrupt("SWI"))); void UNDEF_Routine (void) __attribute__ ((interrupt("UNDEF"))); typedef volatile unsigned int *reg32_t; #include "lpc2220.h" #include "serial.h" #include "flash.h" #include "lcd.h" #include "toolcmd.h" #include "fonty.h" union { unsigned long wbuf[128]; unsigned short sbuf[256]; unsigned char bbuf[512]; } buf; unsigned long checksum; unsigned short count; unsigned long adr; unsigned long numBytes; void putHN(unsigned char pos, unsigned long hn) { draw_string(33,pos,"0x",3,DRAW_PUT); draw_hexW(45,pos,hn,3,DRAW_PUT); } void putInfoVal(unsigned char pos, char *name, unsigned long val) { draw_block(0, pos, 128, 8, 3, DRAW_ERASE); draw_string(0,pos,name,3,DRAW_PUT); putHN(pos, val); } void ACK(void) { serial_puts(ACKTOKEN); } void BACK(void) { serial_puts(BACKTOKEN); } void NACK(void) { serial_puts(NACKTOKEN); } int receiveBuf(void) { unsigned long ccheck; unsigned short cnt, cnt2, cnt3; cnt = count<<2; if(cnt > 512) return 0; checksum = 0; ccheck = 0; cnt2 = 0; #define XFERSIZE 16 while(cnt >= XFERSIZE) { cnt3=XFERSIZE; while(cnt3--) { buf.bbuf[cnt2] = serial_getc(); checksum += buf.bbuf[cnt2++]; } BACK(); cnt -= XFERSIZE; } if(cnt) { while(cnt--) { buf.bbuf[cnt2] = serial_getc(); checksum += buf.bbuf[cnt2++]; } BACK(); } ccheck = serial_getc() << 24; ccheck += serial_getc() << 16; ccheck += serial_getc() << 8; ccheck += serial_getc(); if(ccheck == checksum) { return 1; } drawStatus("Wrong Checksum"); return 0; } int main(void) { unsigned char i; count = 0; adr = 0x00000000; timer = TIMEOUT+1; numBytes = 0; lcd_init(0); IODIR0|=0x10; IOCLR0=0x10; serial_init(); set_font(1); #ifdef RESIDENT draw_string(0, 0,">> FlashTool V0.2-r",3,DRAW_PUT); #else draw_string(0, 0,">> FlashTool V0.2",3,DRAW_PUT); #endif set_font(0); draw_string(0,14,"This tool is licensed under",3,DRAW_PUT); draw_string(0,22,"the GNU GPL 3 or later",3,DRAW_PUT); draw_string(0,34,"(c) 2007 Ch. Klippel",3,DRAW_PUT); draw_string(0,42,"",3,DRAW_PUT); drawStatus("FlashTool ready!"); adr = 0x00000000; while (1) { i = serial_getc(); if(i==HELO_CMD) { serial_puts(HELOTOKEN); drawStatus("Sent HELO"); } else if(i==BULKENABLE_CMD) { putInfoVal(80, "Bulk:", 1); if((adr & 0xFF000000) == 0x80000000 || (adr & 0xFF000000) == 0x82000000) { prepareBulk(adr); drawStatus("Enabled bulk write"); draw_string(100,80,ACKTOKEN,3,DRAW_PUT); ACK(); } else { draw_string(100,80,NACKTOKEN,3,DRAW_PUT); NACK(); } } else if(i==SKIP_CMD) { adr += (serial_getc() << 16); adr += serial_getc(); ACK(); } else if(i==BULKDISABLE_CMD) { putInfoVal(80, "Bulk:", 0); if((adr & 0xFF000000) == 0x80000000 || (adr & 0xFF000000) == 0x82000000) { endBulk(adr); drawStatus("Disabled bulk write"); draw_string(100,80,ACKTOKEN,3,DRAW_PUT); ACK(); } else { draw_string(100,80,NACKTOKEN,3,DRAW_PUT); NACK(); } } else if(i==SETADR_CMD) { adr = serial_getc() << 24; adr += serial_getc() << 16; adr += serial_getc() << 8; adr += serial_getc(); putInfoVal(72, "Addr:", adr); if((adr & 0xFF000000) == 0x40000000 || (adr & 0xFF000000) == 0x80000000 || (adr & 0xFF000000) == 0x82000000) { drawStatus("Address changed"); draw_string(100,72,ACKTOKEN,3,DRAW_PUT); ACK(); } else { draw_string(100,72,NACKTOKEN,3,DRAW_PUT); adr = 0x00000000; NACK(); } } else if(i==FILLBUF_CMD) { count = serial_getc(); putInfoVal(88, "Buf:", count<<2); if(count > 0 && count <= 128) { if(receiveBuf()) { ACK(); } else { goto fail_f; } } else { fail_f: draw_string(100,88,NACKTOKEN,3,DRAW_PUT); count = 0; NACK(); } } else if(i==WRITE_CMD) { putInfoVal(96, "Write:", adr); i = serial_getc(); if(i==WRITEGO_CMD && count > 0) { if(writeBulk((unsigned long) &buf.bbuf, adr, count<<1) == 0) { adr += (count<<2); ACK(); } else { draw_string(100,96,NACKTOKEN,3,DRAW_PUT); NACK(); } } } else if(i==SECTERASE_CMD) { drawStatus("Erasing Flash Sector"); if(eraseSectorAt(adr) == 0) { drawStatus("Erased Flash Sector"); ACK(); } else { drawStatus("Erase Sector FAILED!!"); NACK(); } } else if(i==FULLERASE_CMD) { unsigned char w; w = 0xFF; if((adr & 0xFF000000) == 0x82000000) { drawStatus("Erasing Flash #1"); w = 1; } else { drawStatus("Erasing Flash #0"); w = 0; } if(eraseFlash(w) == 0) { if(w==1) { drawStatus("Erased Flash #1"); } else if(w==0) { drawStatus("Erased Flash #0"); } ACK(); } else { if(w) { drawStatus("Flash #1 Erase FAILED!!"); } else { drawStatus("Flash #0 Erase FAILED!!"); } NACK(); } } else if(i==SETNUMBYTES_CMD) { numBytes = serial_getc() << 24; numBytes += serial_getc() << 16; numBytes += serial_getc() << 8; numBytes += serial_getc(); putInfoVal(104, "NumB:", numBytes); if(numBytes <= 0x00100000) { draw_string(100,104,ACKTOKEN,3,DRAW_PUT); ACK(); } else { draw_string(100,104,NACKTOKEN,3,DRAW_PUT); NACK(); } } else if(i==READ_CMD) { for(adr = 0x40000200; adr < 0x40000210; adr+=4) { putHexW((unsigned long)(*(volatile unsigned long *)(adr))); serial_putc('\n'); } for(adr = 0x80000000; adr < 0x80000010; adr+=4) { putHexW((unsigned long)(*(volatile unsigned long *)(adr))); serial_putc('\n'); } } } return 0; } /* Stubs for various interrupts (may be replaced later) */ /* ---------------------------------------------------- */ void IRQ_Routine (void) { while (1) ; } void FIQ_Routine (void) { while (1) ; } void SWI_Routine (void) { while (1) ; } void UNDEF_Routine (void) { while (1) ; }