diff --git a/TommyPROM/TommyPROM.ino b/TommyPROM/TommyPROM.ino index 243e25f..4f52dbc 100644 --- a/TommyPROM/TommyPROM.ino +++ b/TommyPROM/TommyPROM.ino @@ -19,7 +19,7 @@ #include "XModem.h" -static const char * MY_VERSION = "2.0"; +static const char * MY_VERSION = "2.1"; // Global status @@ -79,6 +79,7 @@ enum { CMD_ERASED, CMD_FILL, CMD_LOCK, + CMD_POKE, CMD_READ, CMD_UNLOCK, CMD_WRITE, @@ -136,6 +137,7 @@ byte parseCommand(char c) case 'e': cmd = CMD_ERASED; break; case 'f': cmd = CMD_FILL; break; case 'l': cmd = CMD_LOCK; break; + case 'p': cmd = CMD_POKE; break; case 'r': cmd = CMD_READ; break; case 'u': cmd = CMD_UNLOCK; break; case 'w': cmd = CMD_WRITE; break; @@ -184,7 +186,7 @@ byte hexDigit(char c) * character. Leading zeroes are not required. * * No error checking is performed - if no hex is found then -* zero is returned. Similarly, a hex string of more than +* defaultValue is returned. Similarly, a hex string of more than * 8 digits will return the value of the last 8 digits. * @param pointer to string with the hex value of the word (modified) * @return unsigned int represented by the digits @@ -428,6 +430,60 @@ void erasedBlockCheck(uint32_t start, uint32_t end) } +/** + * Write a series of bytes from the command line to the PROM. + * + * @param cursor - pointer to command line text + */ +void pokeBytes(char * pCursor) +{ + uint32_t val; + uint32_t start; + unsigned byteCtr = 0; + + enum { BLOCK_SIZE = 32 }; + byte data[BLOCK_SIZE]; + + //first value returned is the starting address + start = getHex32(pCursor, 0); + + while (((val = getHex32(pCursor, 0xffff)) != 0xffff) && (byteCtr < BLOCK_SIZE)) + { + data[byteCtr++] = byte(val); + } + + if (byteCtr > 0) + { + if (!prom.writeData(data, byteCtr, start)) + { + cmdStatus.error("Write failed"); + return; + } + } + else + { + cmdStatus.error("Missing address or data"); + return; + } + delay(100); + + for (unsigned ix = 0; ix < byteCtr ; ix++) + { + byte val = prom.readData(start + ix); + if (val != data[ix]) + { + cmdStatus.error("Verify failed"); + cmdStatus.setValueHex(0, "addr", start + ix); + cmdStatus.setValueHex(1, "read", val); + cmdStatus.setValueHex(2, "expected", data[ix]); + return; + } + } + cmdStatus.info("Poke successful"); +} + + + #ifdef ENABLE_DEBUG_COMMANDS /** * Runs through a range of addresses, reading a single address @@ -535,7 +591,7 @@ void zapTest(uint32_t start) } delay(100); - for (int ix = 0; ix < sizeof(testData); ix++) + for (unsigned ix = 0; ix < sizeof(testData); ix++) { byte val = prom.readData(start + ix); if (val != testData[ix]) @@ -573,25 +629,7 @@ void setup() * executing read or write requestes. **/ -/* 8085 Test programs -byte ledTest[] = -{ - 0xc3, 0x03, 0x80, 0x3e, 0xc0, 0x30, 0x3e, 0xff, - 0x47, 0x3d, 0x05, 0xc2, 0x0a, 0x80, 0xfe, 0x00, - 0xc2, 0x09, 0x80, 0x3e, 0x40, 0x30, 0x3e, 0xff, - 0x47, 0x3d, 0x05, 0xc2, 0x1a, 0x80, 0xfe, 0x00, - 0xc2, 0x19, 0x80, 0xc3, 0x03, 0x80 -}; -byte charTest[] = -{ - 0xc3, 0x03, 0x80, 0x0e, 0x55, 0xf3, 0x06, 0x0b, 0xaf, 0x3e, 0x80, 0x1f, - 0x3f, 0x30, 0x21, 0x19, 0x00, 0x2d, 0xc2, 0x11, 0x80, 0x25, 0xc2, 0x11, - 0x80, 0x37, 0x79, 0x1f, 0x4f, 0x05, 0xc2, 0x09, 0x80, 0x3e, 0xc0, 0x30, - 0x3e, 0x40, 0x30, 0x3e, 0xc0, 0x30, 0x3e, 0x40, 0x30, 0x21, 0xff, 0xff, - 0x2d, 0xc2, 0x30, 0x80, 0x25, 0xc2, 0x30, 0x80, 0xc3, 0x03, 0x80 -}; -*/ - +char line[120]; uint32_t start = 0; uint32_t end = 0xff; byte val = 0xff; @@ -599,7 +637,6 @@ byte val = 0xff; void loop() { uint32_t w; - char line[20]; uint32_t numBytes; Serial.print("\n>"); @@ -647,6 +684,10 @@ void loop() prom.enableSoftwareWriteProtect(); break; + case CMD_POKE: + pokeBytes(line+1); + break; + case CMD_READ: Serial.println(F("Set the terminal to receive XMODEM CRC")); if (xmodem.SendFile(start, uint32_t(end) - start + 1)) @@ -705,6 +746,7 @@ void loop() Serial.println(F(" Esssss eeeee - Check to see if device range is Erased (all FF)")); Serial.println(F(" Fsssss eeeee dd - Fill block on device with fixed value")); Serial.println(F(" L - Lock (enable) device Software Data Protection")); + Serial.println(F(" Psssss dd dd... - Poke (write) values to device (up to 32 values)")); Serial.println(F(" Rsssss eeeee - Read from device and save to XMODEM CRC file")); Serial.println(F(" U - Unlock (disable) device Software Data Protection")); Serial.println(F(" Wsssss - Write to device from XMODEM CRC file")); diff --git a/docs/extending.md b/docs/extending.md index 295dc4f..ee03d35 100644 --- a/docs/extending.md +++ b/docs/extending.md @@ -18,8 +18,8 @@ by the Arduino. Most other chips will not use this addressing method. The 8755A also includes a circuit to switch the programming voltage under software control. This may be useful for other chips that use non-5V programming voltages, although many of these chips, like the 27 series EPROMS, have a programming voltage that remains on for the -entire write and verify cycle. For those chips, it may be easier to simply switch the -programming voltage manually for these chips. +entire write and verify cycle. It may be easier to simply switch the programming voltage +manually for these chips. The basic hardware design, used for the 28C EEPROMs, is much more adaptable to additional chip families. This design uses two shift registers to create 16 dedicated address lines diff --git a/docs/images/tommyprom-console.png b/docs/images/tommyprom-console.png new file mode 100755 index 0000000..8325688 Binary files /dev/null and b/docs/images/tommyprom-console.png differ diff --git a/docs/index.md b/docs/index.md old mode 100644 new mode 100755 index ff18746..8dcffc9 --- a/docs/index.md +++ b/docs/index.md @@ -63,7 +63,7 @@ To use the 8755A version of the code and matching hardware, uncomment PROM_IS_87 comment out the other PROM_IS_xx choices in Configure.h. ## Operation -![TommyPROM Screenshot](images/tp05.png) +![TommyPROM console screenshot](images/tommyprom-console.png) To use the programmer, connect the Arduino USB to the host computer and run a terminal program, such as TeraTerm (Windows) or Minicom (Linux). The Arduino development Serial