Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

most efficient way to save/restore 6502 registers

120 views
Skip to first unread message

Mark Lemmert

unread,
Feb 4, 2016, 2:41:57 PM2/4/16
to
I am wondering if anybody knows why the most Apple II assembly subroutines save/restore registered via the stack (method 1 below), instead of using variables (method 2 below)?

And, what are the advantages and disadvantages are for each method?

Thanks a lot for any insights!


I'm interested in knowing because when writing code where speed is a priority tend to use variables and wondering if I'm missing an important consideration.


The parenthetical numbers in the comment fields below are the clock cycles for each opcode according to the following reference guide (it's on an atari site but since both Apple and Atari use 6502 my understanding is that the opcodes cycle times are the same)

http://www.atarimax.com/jindroush.atari.org/aopc.html



Here is what I've come up with so far:


Advantages (Stack)
======================
Less Memory

Slightly better code readability (I think mainly because it's the standard so
it's immediately obvious what's going on)


Advantages (Variables)
=======================
Speed





=====METHOD 1 (Stack)=====

;SAVE REGISTERS
TXA ;(2)
PHA ;(3)
TYA ;(2)
PHA ;(3)


<SUBROUTINE CODE>


;RESTORE REGISTERS
PLA ;(4)
TAY ;(2)
PLA ;(4)
TAX ;(2)



Total clock cycles: !22
Total Bytes: !16

=====METHOD 1 (Variables)=====


;SAVE REGISTERS
STX SAVED.XREG.LOCAL ;(4)
STY SAVED.YREG.LOCAL ;(4)

<SUBROUTINE CODE>


;RESTORE REGISTERS
LDX SAVED.XREG.LOCAL ;(4)
LDY SAVED.YREG.LOCAL ;(4)



Total clock cycles: !16
Total bytes !24 (for code) + 2 (for variables) = !26

Scott Hemphill

unread,
Feb 4, 2016, 3:31:07 PM2/4/16
to
Mark Lemmert <mark.l...@gmail.com> writes:

> I am wondering if anybody knows why the most Apple II assembly
> subroutines save/restore registered via the stack (method 1 below),
> instead of using variables (method 2 below)?
>
> And, what are the advantages and disadvantages are for each method?
>
> Thanks a lot for any insights!

(1) I think you pretty much covered it. Note that if you do a lot of
saving/restoring, you could (with both schemes) reduce the per instance
memory usage by doing this:

JSR XYSAVE
...
JSR XYRESTORE

You could even omit the call to XYRESTORE if XYSAVE manipulates the
stack by putting the address to XYRESTORE on it, so that the RET from
your subroutine automatically restores the registers.

(2) If your subroutine calls itself recursively, you need to store the
registers on a stack.

(3) If your subroutine doesn't know which memory banks are switched in
(e.g. when processing an interrupt) then you may not want to store the
registers in memory.

(4) Saving the registers in memory allows you to restore them multiple
times.

Scott
--
Scott Hemphill hemp...@alumni.caltech.edu
"This isn't flying. This is falling, with style." -- Buzz Lightyear

Mark Lemmert

unread,
Feb 4, 2016, 10:22:50 PM2/4/16
to
On Thursday, February 4, 2016 at 2:31:07 PM UTC-6, Scott Hemphill wrote:
Scott,

Thanks for the reply!

(1) Great idea. Perfect for programs with plenty of speed and tight on memory.

(2)-(4): This is just the kind of insight I was hoping to gain...I figured there was probably some more advanced bigger picture I was missing on the stack and these examples nail it.


Thanks again.

Michael Barry

unread,
Feb 4, 2016, 11:21:49 PM2/4/16
to
On Thursday, February 4, 2016 at 7:22:50 PM UTC-8, Mark Lemmert wrote:
> ...

If your subroutines are in RAM, and you do not need them to be re-
entrant and/or recursive, you could try self-modifying code:

subroutine:
stx subzzz-3
sty subzzz-1
...
...
ldx #00 ; dummy operand
ldy #00 ; dummy operand
subzzz:
rts

It's just as fast as zero-page variables, and trades a couple
of bytes of zero-page for a couple of bytes of code space.

Mike B.

wss...@gmail.com

unread,
Feb 5, 2016, 12:20:13 AM2/5/16
to
First off, I am a big fan of self-modifying code on 6502 processors. I like this example of register saving and reloading and I also like to use self-modifying code for manipulating things through pointers. For example, to copy memory.

Second off, I am a fan of using 65c02 opcodes. Given than enhanced IIes, IIcs, and IIgses are the vast majority of machines still being actively used, it seems reasonable to do so, in my opinion. Therefore:

; Save Registers
pha
phy
phx
...
; Restore Registers
plx
ply
pla
rts

works great for me.
0 new messages