Date : Thu, 10 Jun 1993 09:36:01 BST
From : ajcd@...
Subject: m/c optimisations
From: Mik Davis <davism@...>
>
> I have a piece of machine code, written using the BASIC assembler which JUST
>fits in the memory available to it. I would like to make it smaller if I can. I
>have made all the size optimisations I can think of. I was wondering if anyone
>out there knows of any tips which would help me to reduce the size of my
>program in memory.
> I am not interested in speed of execution here - only in memory used.
My favourite optimisation techniques include;
1) Examine the pre-and post-conditions for each block or the program
carefully; you can often get away with branches instead of jumps by branching
on some known flag state. You can also avoid setting or clearing flags (esp.
carry) often. (For example, if you add two numbers which you know won't cause
a carry set, like an address and data size, you don't need to clear the carry
before another add, and you can BCC immediately after the code also.)
2) You can use BIT zero-page and BIT absolute (&24 and &2C) as skip 1 or 2
bytes opcodes, if you don't care about the flag state afterwards. This is
useful for a fall-through in case-like statements; e.g.
.one LDA #1 \ entry point
EQUB &2C \ skip next operation
.two LDA #2 \ entry point
EQUB &2C \ skip next operation
.four LDA #4 \ entry point
EQUB &2C
.eight LDA #8 \ entry point
AND mask \ use A as a mask
...
This saves on 1 byte for a branch after each LDA.
3) Use negative zero-page X indexing. If you use zero-page,X indexing, the
6502 doesn't carry the address over to page one if X+zp_address is greater
than &FF. You can use this for multi-byte operations (e.g. add or subtract)
where you can't perform a CPX or CPY in between (which resets the carry
state). e.g., to add two numbers in zero page together:
LDX #&FC \ -4
CLC
.add LDA one+4,X
ADC two+4,X
STA three+4,X
INX
BNE add
4) Use the carry set and clear for adding/subtracting an extra one. For
example, to print a hexadecimal digit, you can do:
print_nibble AND #&F \ print nibble
CMP #10
BCC print_digit
ADC #ASC"A"-ASC"0"-11 \ C is set: A+1+'A'-'0'-1 == A+'A'-'0'
print_digit ADC #ASC"0" \ C is always clear here
JMP oswrch
5) Use EOR for comparisons. This has the advantage that it doesn't affect the
carry, and you can recover the data by EORing again.
a.
--
Angus Duggan, Department of Computer Science, | Jobless, Phdless, clueless
University of Edinburgh, The King's Buildings, | PHONE: +44(0)31 650 5126
Mayfield Road, Edinburgh EH9 3JZ, Scotland. | INET: ajcd@...