Console description

I was asked to dump the built-in game from Intellivision X2 console: This is a battery powered console, with audio+video RCA jack that is directly plugged into TV. Second joystick can be connected to the first one for two player games. Built-in cartridge consists of 15 Atari-based minigames: Space Armada, Night Stalker, Astro Smash, Buzz Bombers, Frog Bog, Pinball, Tennis, Soccer, Beach Volleyball, Long Drive Golf, Space Gunner, Maze Shoot, Football, Hocker, Baseball Inside each joystick there is a blob controler that has pinout similar to: UM6582
First joystick has also small PCB with two blobs: Left one contains games (PRG-ROM + CHR-ROM + mapper). It turns out to be mapper 176. Right one is Nes-On-Chip (CPU + PPU + RAM + VRAM + logic). It is smallest fully complete board I have ever seen: chip, crystal (21.477 MHz), video and audio amplifier. Pinout matches the UM6561, but because the built-in game does not use interrupts and CHR-RAM, there is no /IRQ and PPU /WE routed out of the chip. Top 10 pin header connects with the joystick main PCB: --. 01| $4016 CLK (leftmost) 02| OUT0 03| GND 04| +5V 05| $4016 D0 06| $4017 CLK 07| $4017 D0 08| /RESET 09| amplified video out 10| amplified audio out (rightmost) --'

First idea of dumping

After I analyzed this tiny PCB I was thinking about an efficient way of dumping it, because soldering almost 60 wires (PPU A, PPU D, CPU D and some of the CPU A) to those small vias or even thin traces (because some of the signals are going from one blob to another without any via) is ridiculous. Also, that would require the NES-On-Chip to have all its address and data bus lines disabled (tristate) in order for dumper to be able to control them. I did not test how it behaves while /RESET is asserted, maybe it indeed disables all its lines (or at least those on CPU side) And finally, there could be issues with the mapper reseting itself state if it detects no activity on M2 for longer period of time.
.---------------------. .-----------. | PRG ROM CPU A |------+-----------| | | + CPU D |------|+----------| N E S | | CHR ROM PPU A |------||+---------| o n | | + PPU D |------|||+--------| c h i p | | mapper /ROMSEL |------||||+-------| | | R/W |------|||||+------| | '---------------------' |||||| `-----------` to dumper
This is why I like the approach of many famiclone blob cartridges (especially from JY Company), where all lines going from mapper to memories that do not have vias, have artificial testpads, where wires can be soldered.

Second idea of dumping

Some time ago when I had console with built-in unique games to be dumped, I creaded a special cartridge that helped me in that job: It consisted of a flash memory with asm code, that was executed by the console processor. This code caused the internal games to be read and programmed into the flash memory of cartridge. Then it could be removed, plugged inside kazzo and read back on the PC. Unfortunately here is no cartridge connector, but idea will be similar. Instead of soldering memory chip + socket that would need to be removed, plugged back into programmer, read back, and so on, I decided to make a dedicated board with microcontroller that would help to transfer all the data to PC without any more touching the small fragile board. And instead of ROM, there will be RAM because it can be written by microcontroler affter power-up and writing RAM is faster than programming flash. Ok, so my idea is to solder external RAM. 256 bytes should be enough, so thats CPU D7..0 + CPU A7..0
console's built-in games NES-On-Chip .------------------------. .-----------------------. | PRG ROM CPU A |-----+------------| | | + CPU D |-----|-+----------| N E S $4016.0|----+ | CHR ROM PPU A |-----|-|----------| o n $4016.C|---+| | + PPU D |-----|-|----------| c h i p OUT0 |--+|| | mapper /PRG |--+ | | +-+----| /ROMSEL | ||| | R/W |--|--|-|---|-|-+--| R/W | ||| '------------------------' | R R R R R '-----------------------' ||| | a b c d e ||| .------------------------. | | | | | | .----------------------. ||| | A7..A0|--|--+-|---|-|-|---| |--+|| | D7..D0|--|----+---|-|-|---| |---+| | /CE|--|--------|-+-|---| RAM /CE |----+ | /WE|--|--------|---+---| RAM /WE | .------. | | +--------+-------| PRG /CE USB|-----------| PC | '------------------------' '----------------------' '------' external RAM (256bytes) microcontroller
* Resistors Ra (x8), Rb (x8) and Re will let the microcontroler to freely control RAM's address and data bus and thus read/write to the external RAM, no matter what the Nes-On-Chip is doing on the address/data bus. If microcontroller tristates those lines, Nes-On-Chip can red/write from the RAM. * If Microcontroller drives PRG /CE with 1 and tristates RAM /CE, 256bytes of ram are mapped across $8000-$ffff and console's built in games are disabled * If Microcontroller drives RAM /CE with 1 and tristates PRG /CE, RAM is disabled and cartridge is enabled So the main idea is as follows: * After power up, microcontroller does nothing to the console so it works normally * When it receives special command from USB (CMD_INJECT_START), it puts NES-On-Chip into reset, fills the RAM with `dumping program` (also received via USB), disables the cartridge, enables RAM and deasserts NES-On-Chip reset. Because RAM is mapped at $8000-$ffff, it immediatelly starts executing code from here * `Dumping program` copies itself into nes-on-chip 2kB internal RAM (presumably $700-$7ff) and then it does the whole job: * enables cartridge, reads 256 bytes from the PRG, write it at $600-$6ff, disables cartridge and enables RAM, copies the data from $600-$6ff to RAM and "triggers" microcontroller to pass the data from RAM to PC. * after it is done, microcontroller triggers NES on chip to continue for next chunk of data, untill all data is ripped. * Reading CHR ROM would be done via $2007, so no extra wires to the PPU A/PPU D are required * All pins, where wires need to be soldered are marked below: Most of the pins have (tiny) vias to solder, but few of them (D7, D6, R/W, /ROMSEL) need scraping soldermask out of the tiny trace. Plus also /ROMSEL line need to be cut into half and soldered two wires on each side of it, because microcontroller need to control when cartridge is disabled and enable. So I designed an adapter for that purpose. Initially I preferred to use Atmega8, but it has not enough pins, so I decided on Atmega64. AUDIO/VIDEO connectors are for debugging purposes. And after soldering the wires: What about the communication between Nes-on-Chip and microcontroller? How it can give a sign to transfer the content of memory to PC? Using joypad pins seems to be a good idea. Though microcontroller is much slower that nes-on-chip, so if nes-on-chip did $4016 read, atmega would probably even not notice that $4016.clk line went down for a while. So OUT0 and $4016.D0 are used to cycle between RAM disabled/cartridge enabled and RAM enabled/cartridge disabled: powerup --------+ \./ .-------------------. .-------------------. +--> | RAM disabled | --> [NES ON CHIP does ] --> | RAM enabled | --+ | | cartridge enabled | [rising edge on OUT0 ] | cartridge disabled| | | '-------------------' '-------------------' | | | +----------------------------------------------------------------------------------+ * OUT0 is used as a line from nes-on-chip to atmega, * $4016.D0 is used as a line from atmega to nes-on-chip. 1 2 3 4 5 6 OUT0 ____------______----- $4016.D0 _______------________ <-value set by atmega, nes-on-chip read oppoite of that RAM-/CS 000000011111111111111 ROM-/CS 111111100000000000000 1) idle state - both lines low 2) nes-on-chip asks atmega to turn OFF RAM and turn ON cartridge: it drives OUT0 with 1 3) atmega waits for a request from PC to read data. If it arrives, it transfers all the data from onboard RAM to PC, disables RAM, enables ROM and drives $4016.D0 with 1 4) when NES sees $4016.D0 going high, it drives OUT0 with 0 5) when atmega sees that, it drives $4016.D0 with 0 6) then NES reads next chunk of ROM into its internal memory and when it is ready to write it to onboard RAM, it brings OUT0 up like in 2

Main flow

So basically this make slave device from NES on CHIP that can execute any arbitrary code sent from PC. First code was sent to dump PRG, then to dump CHR. I was able to successfully rip the game (512kb PRG + 512 kB CHR)