123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144 |
- ; code: language=asm-collection tabSize=8
- ; Requirements:
- ; This function must be RELOCATABLE (only relative jumps), and use NO RAM or STACK.
- ; These restrictions lead to somewhat long-winded, repetative code.
- ;; March C- algorithm:
- ;; 1: (up w0) write each location bottom to top with test value
- ;; 2: (up r0,w1) read each location bottom to top, compare to test value, then write complement
- ;; 3: (up r1,w0) read each location bottom to top, compare to complement, then write test value
- ;; 4: (dn r0,w1) read each location top to bottom, compare to test value, then write complement
- ;; 5: (dn r1,w0) read each location top to bottom, compare to complement, then write test value
- ;; 6: (dn r0) read each location top to bottom, compare to test value
- ; Arguments:
- ; hl = current memory position under test
- ; bc = bytes remaining to test
- ; iy = test data structure
- ; returns:
- ; e = all errored bits found in this block/bank/range of memory
- ; destroys: a,bc,d,hl
- ; preserves: ix
- memtest_init:
- xor a
- ld e,a ; reset error accumulator
- ret
- memtest_absent:
- ld b,h
- ld c,1
- cpl ; A := FF
- .redo ld (hl),a ; write FF to base
- cpl ; A := 0
- ld (bc),a ; write 00 to base+1
- cp (hl) ; compare to base (should be FF, should not match)
- jr z,.allbad ; if they match, all bits are bad, but double-check
- cp 0 ; are we on the first round?
- jr z,.redo ; yes, redo with reversed bits
- ret ; didn't find missing ram, exit without error
- .allbad:
- ld e,$FF ; report all bits bad
- ret
- memtest_march_w_up:
- .loop: ; fill upwards
- ld (hl),d
- inc hl
- dec bc
- ld a,c
- or b
- jr nz,.loop
- ret
- memtest_march_rw_up:
- .loop:
- ld a,(hl)
- cp d ; compare to value
- jr z, .cont ; memory changed, report
- xor d ; calculate errored bits
- or e
- ld e,a ; save error bits to e
- ld a,d ; reload a with correct value
- .cont:
- cpl ; take the complement
- ld (hl),a ; write the complement
- inc hl
- dec bc
- ld a,c
- or b
- jr nz,.loop
- ret
-
- memtest_march_rw_dn:
- add hl,bc ; move to end of the test area
- dec hl
- .loop:
- ld a,(hl)
- cp d ; compare to value
- jr z, .cont
- xor d ; calculate errored bits
- or e
- ld e,a ; save error bits to e
- ld a,d ; reload a with correct value
- .cont:
- cpl ; take the complement
- ld (hl),a ; write complement
- dec hl
- dec bc
- ld a,c
- or b
- jr nz,.loop
- ret
- memtest_march_r_dn:
- add hl,bc ; move to end of the test area
- dec hl
- .loop:
- ld a,(hl)
- cp d
- jr z,.cont
- xor d ; calculate errored bits
- or e
- ld e,a ; save error bits to e
- ld a,d ; reload a with correct value
- .cont:
- dec hl
- dec bc
- ld a,c
- or b
- jr nz,.loop
- ret
- mtmredo:
- ld a,d
- cp 0 ; if our test value is 0
- ld d,$55
- jr z,mtm1_bounce ; then rerun the tests with value $55
- mtm_done:
- sub a ; set carry flag if e is nonzero
- or e
- mtm_return:
- ret z
- scf
- ret
- memtest_march:
- xor a
- ld e,a ; reset error accumulator
- push hl ; save the test regs
- push bc
- call memtest_absent
-
- ld d,0
- .redo:
- memtest_split_end equ $
- ;-----------------------------------------------------------------------------
|