Page 3 of 5
Re: A simple 6502 computer (doesn't work though)
Posted: Tue Jun 25, 2019 5:24 pm
by Dr Jefyll
It might be easier to start with the not-working program and gradually NOP out the bits that don't exist in the working one. If it's still not working, start deleting the NOPs.
Interesting. So, the presence or absence of the NOP's will alter which addresses the instructions get mapped to.... and if altering the addresses produces a change (which it ought not to do) then we conclude some address lines have been switched? Just trying to be sure what you mean.
As for suggesting you overlooked content from upthread, I hope it's clear there's no criticism implied -- especially since I myself have very recently been found
guilty!

Re: A simple 6502 computer (doesn't work though)
Posted: Tue Jun 25, 2019 8:37 pm
by jgroth
Well, 6500 (and 6800) series processors use the Phi2-low time to prepare for a data transfer and the Phi2-high time to actually perform the transfer. Preparing for the transfer entails the propagation of a new address onto the address bus... and it also entails a potential change of "ownership" of the
data bus. During write cycles the data bus is driven by the CPU, and during read cycles any of several other devices (RAM, ROM, I/O) may take their turn.
Getting the devices to start and stop driving the bus is a somewhat inexact science. One of the reasons is, the devices don't instantly respond to changes on their /CE and /OE inputs -- and, the delay can only be predicted approximately (the margin of error could easily be 10 or 20 ns -- or more). This implies a threat of short-lasting bus collisions (bus contention). For example, in a handover from Device A to Device B, there's a risk Device B may begin driving the bus before Device A has stopped -- and for 10 or 20 ns the computer's Gnd and Vcc network gets blasted with a large current spike.
It's not unusual to see designs which ignore this issue (the collision
is brief, and arguably may be considered tolerable). But the solution is simple. Just arrange your glue logic so no device drives the data bus during the Phi2-low time. This guarantees a big, fat 500 ns timing "cushion" -- enough to soak up any variability and ensure that every bus handover is courteous and gentle.
( I can't specifically explain how a large current spike might produce the symptom we're seeing here, and that's why my concern is only a hunch. But clearly we have a computer that's acting "funny" -- it seemingly executes some code correctly, and other code not. And "funny" behavior is often the result of noise issues such as those caused -- especially on breadboards -- by current spikes. )
I'll be interested to learn the result of the experiment!
-- Jeff
Well moving /OE to /Q didn't do anything. Still doesn't work. I've noticed I thing though. Gareth's loop
Code: Select all
loop: dec via1rb
jsr delay
bra loop
works fine ie the probe goes from high to low to high. But what doesn't work is code like this:
Code: Select all
loop: lda #$00
sta via1rb
jsr delay
lda #$ff
sta via1rb
jsr delay
bra loop
which should essentially do the same thing. If I change lda #$00 to lda #$55 and the second lda to lda #$aa which should blink the probe but the VIA gets stuck on $55 and I can't change the value after that no matter what I've tried.
Is my VIA broken in some way? BTW I've double checked that every wire goes where it should go (ie everything is connected as the schema shows).
/Johan
Re: A simple 6502 computer (doesn't work though)
Posted: Tue Jun 25, 2019 8:45 pm
by GARTHWILSON
I've noticed I thing though. Gareth's loop
Code: Select all
loop: dec via1rb
jsr delay
bra loop
works fine ie the probe goes from high to low to high. But what doesn't work is code like this:
Code: Select all
loop: lda #$00
sta via1rb
jsr delay
lda #$ff
jsr delay
bra loop
which should essentially do the same thing. If I change lda #$00 to lda #$55 and the second lda to lda #$aa which should blink the probe but the VIA gets stuck on $55 and I can't change the value after that no matter what I've tried.
Is my VIA broken in some way? BTW I've double checked that every wire goes where it should go (ie everything is connected as the schema shows).
You'll need STA VIA1RB after the LDA #$FF; but you did do the STA on page 1 of the topic, and it didn't work; so there's probably something else.
After all the VIAs we put in products two decades ago, the only failure I ever saw was one where a bond wire apparently let loose as an infant mortality, shortly after it was put into service. We have never gotten bad silicon, in this or any of the other hundreds of thousands (or millions?) of new ICs we've put in products. You do of course always have to be careful to prevent ESD damage in handling before the product is finished and packaged.
Edit: BTW, there's no "e" in my name. Apparently "Gareth" is a common name in the UK; but my name is just "Garth."
Re: A simple 6502 computer (doesn't work though)
Posted: Wed Jun 26, 2019 3:54 am
by Dr Jefyll
what doesn't work is code like this:
[...]
which should essentially do the same thing.
The routine that writes $55 then $AA will cause all 8 bits of the VIA port to toggle at the same rate. In contrast, the routine that decrements will cause bit0 of the VIA port to toggle at a certain rate.... but on bit1 the rate will be half, and on bit2 it'll be half again, and so on. The rate on bit7 will, comparatively, be very slow indeed. Sorry if this seems obvious. But might your unexpected result simply be a toggle rate that's a great deal higher or lower than expected?
Hmm. What happens if you...
Code: Select all
loop: dec via1rb
jsr delay
dec via1rb
jsr delay
bra loop
By playing around you might uncover a clue. Sorry, at the moment I don't have any other ideas...

Good luck, have fun, and keep us posted!
Re: A simple 6502 computer (doesn't work though)
Posted: Wed Jun 26, 2019 9:19 am
by John West
Code: Select all
loop: dec via1rb
jsr delay
bra loop
works fine ie the probe goes from high to low to high. But what doesn't work is code like this:
Code: Select all
loop: lda #$00
sta via1rb
jsr delay
lda #$ff
sta via1rb
jsr delay
bra loop
That's curious! Is that the only difference between the two? They won't have exactly the same behaviour, but they both should do something observable.
One difference between the two will be the frequency. It should be low enough that even a very poor logic probe can see the activity, but just in case: can it see bit 0 toggling on the first version? That should be the same frequency as every bit on the second.
Just to satisfy my curiosity, could you post a listing output from the assembler for each version? Something that shows which address each instruction goes to. The possibility of something position-dependent is still nagging at me.
Re: A simple 6502 computer (doesn't work though)
Posted: Thu Jun 27, 2019 4:00 pm
by jgroth
Code: Select all
loop: dec via1rb
jsr delay
bra loop
works fine ie the probe goes from high to low to high. But what doesn't work is code like this:
Code: Select all
loop: lda #$00
sta via1rb
jsr delay
lda #$ff
sta via1rb
jsr delay
bra loop
That's curious! Is that the only difference between the two? They won't have exactly the same behaviour, but they both should do something observable.
One difference between the two will be the frequency. It should be low enough that even a very poor logic probe can see the activity, but just in case: can it see bit 0 toggling on the first version? That should be the same frequency as every bit on the second.
No problem seeing the probe going from high to low to high and so on. That goes for all bits (ie PB0-PB7)
Just to satisfy my curiosity, could you post a listing output from the assembler for each version? Something that shows which address each instruction goes to. The possibility of something position-dependent is still nagging at me.
Sure, here is the list (this code doesn't work on the NAND-board BTW, but does on the ref-board:
Code: Select all
; 64tass Turbo Assembler Macro V1.52.1237? listing file
; 64tass -Demulator=false -o via.bin --nostart --no-monitor --line-numbers --tab-size=1 --list=via.lst via.asm
; Thu Jun 27 16:48:56 2019
;Line ;Offset ;Hex ;Source
;****** Command line definitions
=false emulator=false
:1 ;****** Processing input file: via.asm
5 =$6000 via1base = $6000
7 =24576 via1rb = via1base+0 ; write output register b, read input register b
8 =24577 via1ra = via1base+1 ; write output register a, read input register a
9 =24578 via1ddrb = via1base+2 ; data direction register b
10 =24579 via1ddra = via1base+3 ; data direction register a
12 .8000 nmi:
13 .8000 irq:
18 .8000 coldstart:
20 .8000 a2 ff ldx #$ff
21 .8002 9a txs ;Initialise stack register
30 .8003 8e 02 60 stx via1ddrb ; set all PB pins to be outputs
31 .8006 loop:
32 .8006 a9 00 lda #$00
34 .8008 8d 00 60 sta via1rb
36 .800b 20 18 80 jsr delay ; wait for a while
37 .800e a9 ff lda #$ff
38 .8010 8d 00 60 sta via1rb
43 .8013 20 18 80 jsr delay
44 .8016 80 ee bra loop
47 .8018 delay:
49 .8018 loop1:
50 .8018 a2 ff ldx #$ff
51 .801a loop2:
52 .801a a0 ff ldy #$ff
53 .801c loop3:
54 .801c 88 dey
55 .801d d0 fd bne loop3
56 .801f ca dex
57 .8020 d0 f8 bne loop2
58 .8022 60 rts
62 >fffa 00 80 .word nmi ;NMI
63 >fffc 00 80 .word coldstart ;RESET
64 >fffe 00 80 .word irq ;IRQ
;****** End of listing
This code works on both boards.
Code: Select all
; 64tass Turbo Assembler Macro V1.52.1237? listing file
; 64tass -Demulator=false -o via_test_prg.bin --nostart --no-monitor --line-numbers --tab-size=1 --list=via_test_prg.lst via_test_prg.asm
; Mon Jun 24 21:09:26 2019
;Line ;Offset ;Hex ;Source
;****** Command line definitions
=false emulator=false
:1 ;****** Processing input file: via_test_prg.asm
5 =$6000 via1base = $6000
6 =24576 via1rb = via1base+0 ; write output register b, read input register b
7 =24578 via1ddrb = via1base+2 ; data direction register b
10 .8000 nmi:
11 .8000 irq:
16 .8000 coldstart:
17 .8000 a2 ff ldx #$ff
18 .8002 9a txs ; Initialise stack pointer register
19 .8003 8e 02 60 stx via1ddrb ; and make PB0-PB7 all outputs.
25 .8006 ce 00 60 loop: dec via1rb ; PB7 will cycle high & low
26 .8009 20 0e 80 jsr delay ; at about 2/3 second at 1MHz, PB6 at
27 .800c 80 f8 bra loop ; twice that rate, PB5 4x that rate, etc..
31 .800e delay:
32 .800e a2 ff ldx #$ff
33 .8010 a0 ff loop2: ldy #$ff
34 .8012 88 loop3: dey
35 .8013 d0 fd bne loop3
36 .8015 ca dex
37 .8016 d0 f8 bne loop2
38 .8018 60 rts
43 >fffa 00 80 .word nmi ;NMI
44 >fffc 00 80 .word coldstart ;RESET
45 >fffe 00 80 .word irq ;IRQ
;****** End of listing
Re: A simple 6502 computer (doesn't work though)
Posted: Thu Jun 27, 2019 4:53 pm
by Chromatix
All the code (besides the vectors) is within the first 32 bytes of the ROM for the decrement test, but not for the inversion test. Does inserting ten NOPs between the 'BRA loop' and 'delay:' - to move the latter subroutine to a consistent position - make the decrement test fail? These are bytes that would never be executed.
Re: A simple 6502 computer (doesn't work though)
Posted: Thu Jun 27, 2019 5:06 pm
by jgroth
All the code (besides the vectors) is within the first 32 bytes of the ROM for the decrement test, but not for the inversion test. Does inserting ten NOPs between the 'BRA loop' and 'delay:' - to move the latter subroutine to a consistent position - make the decrement test fail? These are bytes that would never be executed.
No, the probe is blinking as it should.
Re: A simple 6502 computer (doesn't work though)
Posted: Fri Jun 28, 2019 2:19 am
by Chromatix
Try:
Code: Select all
STZ via1rb
JSR delay
DEC via1rb
JSR delay
BRA loop
That should produce the "inversion" type output with 4 bytes smaller code.
Re: A simple 6502 computer (doesn't work though)
Posted: Fri Jun 28, 2019 4:57 am
by floobydust
Tis a puzzling problem... looking at the code, there is one main difference between the working and non-working code in accessing the 6522.
- The working code uses a DEC instruction, which means it reads the contents of the port register into the A reg, decrements whatever was read by one, then writes it back to the port register.
- The non-working code only uses a STA instruction, so the port is only written to and never read from.
Perhaps there is some timing issue of control signals where reading and writing from/to the 6522 works but writing only doesn't. Or perhaps there is some signal ringing on the breadboard causing a problem.
Re: A simple 6502 computer (doesn't work though)
Posted: Fri Jun 28, 2019 5:13 am
by Chromatix
My suggestion immediately above might help in that regard, as it incorporates both a direct store and a RMW operation.
Re: A simple 6502 computer (doesn't work though)
Posted: Fri Jun 28, 2019 1:01 pm
by floobydust
My suggestion immediately above might help in that regard, as it incorporates both a direct store and a RMW operation.
True, your coding example would also do the same.
Looking at the schematic again, I would also suggest moving the clock line of the W65C22 (pin 25) to the clock out line of the W65C02 (pin 39). I'm aware of what the current datasheet from WDC states on timing, but I've been running all WDC parts using the clock 2 out line to drive 65xx support chips at clock speeds from 1MHz to 10MHz without any issue. I think it's worth a try.
Re: A simple 6502 computer (doesn't work though)
Posted: Sat Jun 29, 2019 6:38 pm
by jgroth
So I tried this code:
Code: Select all
coldstart: .block
ldx #$ff
txs ;Initialise stack register
stx via1ddrb ; set all PB pins to be outputs
loop:
stz via1rb
jsr delay ; wait for a while
dec via1rb
jsr delay
bra loop
.bend
delay: .proc
ldx #$ff
loop2:
ldy #$ff
loop3:
dey
bne loop3
dex
bne loop2
rts
.pend
and the via gets stuck on low.
Re: A simple 6502 computer (doesn't work though)
Posted: Sun Jun 30, 2019 4:27 am
by barrym95838
This might be a silly notion, but are you certain that you're always getting a clean rts from your jsr delay? Would it be helpful to try a version that in-lines the delay?
Re: A simple 6502 computer (doesn't work though)
Posted: Sun Jun 30, 2019 1:50 pm
by LIV2
Should the A14 input of the SRAM be connected to A14 instead of GND so that writes to IO space don't write to the lower half of the RAM?