Here is what I am trying to do. I have two 16f688 chips communicating with the hardware serial ports. I have a Nintendo NES controller attached to the transmitter chip and an LCD attached to the receiver chip.

In theory, the transmitter chip sends a pulse to the controller down the latch line, reads the state of the data line and stores the value in the EEPROM. Then the transmitter sends a pulse down the clock line, which tells the controller to send the state of the second button down the data line. This process repeats 8 times so all button states can be stored. The controller will send the button states in this order: A, B, Start, Select, Up, Down, Left, Right. The transmitter then sends a trigger ("I") and the first button state to the receiver, and repeats 8 times for each button.

The receiver waits for the trigger ("I"), then stores the state of the first button in a variable. The variable is saved to the EEPROM and the process repeats 8 times. The receiver then will read the EEPROM and display the button state of each button on the screen.


A few things aren't working right though. First off, the A button is the only one that will respond, but the controller works fine when playing Nintendo. And second, the A button will change the state of all buttons on the LCD screen. The screen should be set up to display a 1 when the corresponding button is open, and a 0 when it's pressed, but instead of getting "0 1 1 1 1 1 1 1" when I press A, I get "0 0 0 0 0 0 0 0".

Everything else appears to work fine. If anyone could take a look at my code it would be greatly appreciated. I am using Microcode Studio with a melabs U2 programmer and MPASM assembler. Here are some websites that may help with understanding how the NES controller works.

http://www.zero-soft.com/HW/USB_NES_old/
http://web.mit.edu/tarvizo/web/nes-controller.html
http://www.nxp.com/documents/data_sheet/HEF4021B.pdf

and my codes:

transmitter
Code:
include "modedefs.bas"

ANSEL = 0
CMCON0 = 0

'~~~~~Serial Transmitter Definitions~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

DEFINE HSER_RCSTA 90h ' Enable Serial PORT
DEFINE HSER_TXSTA 24h ' Enable transmit
DEFINE HSER_SPBRG 25 ' set USART to 9600 baud (when BRGH=1)
DEFINE HSER_CLROERR 1 ' Enable automatic overrun error
DEFINE LOADER_USED 1


'~~~~~Variables~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
LATCH var portc.0   'pin 10   
CLK var portc.1     'pin 9
DAT var portc.2     'pin 8

SerData var byte
CNT var byte

serdata = 0
cnt = 0
dat = 1

'pause 2000


'~~~~~Main Program~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Main:

low latch      'reset LATCH line
low clk        'reset CLK line


'~~~~~Read state of controller buttons and write them to EEPROM~~~~~~~~~~~~~~~~~~~~

pulsout latch, 12    'send a 12us high pulse down latch line to controller

'pauseus 1            '1us     evens out initial CLK timing

for cnt = 0 to 7     '1us     set CNT value
write cnt, dat       '1us     write state (1 or 0) of DAT pin to CNT value 
                     '        EEPROM location
pauseus 4            '4us     
                     '6us total
                     
pulsout clk, 6       '6us     send 6us pulse down CLK line so controller
                     '        will send next button state
next                 '1us     repeat 8 times
                     '7us total
                     
                     
'~~~~~Send state of controller buttons to receiver~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

cnt = 0                'reset CNT value

for cnt = 0 to 7       'read EEPROM and send data serially 8 times
read cnt, serdata      'read EEPROM at CNT value location
hserout ["I", serdata] 'send wait trigger "I" and state of each button to receiver
next

goto main

and the receiver

Code:
ANSEL  = 0
TRISC = 0
CMCON0 = 0

DEFINE LCD_DREG PORTC 'Define PIC port used for LCD Data lines
DEFINE LCD_DBIT 0 'LCD Data Starting Bit = Bit 0 or 4
DEFINE LCD_EREG PORTA 'Define PIC port used for E line of LCD
DEFINE LCD_EBIT 5 'Define Port pin used for E connection
DEFINE LCD_RSREG PORTA 'Define PIC port used for RS line of LCD
DEFINE LCD_RSBIT 4 'Define Port pin used for RS connection
DEFINE LCD_BITS 4 'Define the 4 bit communication mode to LCD
DEFINE LCD_LINES 2 'Define using a 2 line LCD
DEFINE LCD_COMMANDUS 2000 'Define delay time between sending LCD commands
DEFINE LCD_DATAUS 50 'Define delay time between data sent.

Pause 500 ' Wait for LCD to startup


'~~~~~Serial Receiver Definitions~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~`
DEFINE HSER_RCSTA 90h ' Enable Serial PORT
DEFINE HSER_TXSTA 24h ' Enable transmit
DEFINE HSER_SPBRG 25 ' set USART to 9600 baud 
DEFINE HSER_CLROERR 1 ' Enable automatic overrun error
DEFINE LOADER_USED 1


'~~~~~Variables~~~~~~~~~~~~~~~~~~

SerData var byte
SerData2 var byte
CNT var byte


'~~~~~Main Program~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
              '"                "
lcdout $fe, 1, " NES CONTROLLER "

Main:

for cnt = 0 to 7                'set CNT value
hserin [Wait ("I"), serdata]    'wait for trigger "I" and store the button
                                'state in SerData     
write cnt, serdata              'write button state to CNT value EEPROM location
next                            'repeat 8 times

CNT = 0                         'reset CNT value
lcdout $fe, $c0                 'put LCD cursor to beginning of second line
for cnt = 0 to 7                'set CNT value               
read cnt, serdata2              'read EEPROM CNT value location and store
                                'value in SerData2
lcdout dec1 serdata2, " "       'display SerData2 value and move right one space
next                            'repeat 8 times

goto main