Old but Gold: in search for (forgotten) tricks

Programming the 6502 microprocessor and its relatives in assembly and other languages.
Post Reply
User avatar
Broti
Posts: 28
Joined: 07 Sep 2023
Location: Moers, Germany

Old but Gold: in search for (forgotten) tricks

Post by Broti »

Well technically not just a 6502 only topic.
Since I wasn't around in the early days of computing in the '70s and don't know where (magazines or books) to start:
I'm searching for those vintage programming tricks like the BIT skip, which also appears e.g. in the source of Altair BASIC (8080: LXI) or GW-BASIC (8088: MOV).
Do you know any?
ROR A? Where we're coding, we don't need A.
User avatar
BB8
Posts: 57
Joined: 01 Nov 2020
Location: Tatooine

Re: Old but Gold: in search for (forgotten) tricks

Post by BB8 »

User avatar
Broti
Posts: 28
Joined: 07 Sep 2023
Location: Moers, Germany

Re: Old but Gold: in search for (forgotten) tricks

Post by Broti »

I already knew these two threads but thanks anyway :wink:
(And the code section on this site)
They might be helpful for others. *thumb up*
ROR A? Where we're coding, we don't need A.
User avatar
BB8
Posts: 57
Joined: 01 Nov 2020
Location: Tatooine

Re: Old but Gold: in search for (forgotten) tricks

Post by BB8 »

Code: Select all

; is min <= .A <= max
CLC
ADC #$FF-max
ADC #max-min+1
BCS yes
 
SEC
SBC #min
SBC #max-min+1
BCC yes

CLC                           ; by Mike Barry
ADC #$FF-max
CMP #$FF-min+1
BCS yes
 
CMP #min
BCC LessThanMin
CMP #max+1
BCS MoreThanMax
; here is   min <= .A <= max
 
 
; .A = M- .A
SEC
EOR #$FF
ADC M
 
CLC
SBC M
EOR #$FF
 
 
; SwapNibbles
ASL
ADC #$80
ROL
ASL
ADC #$80
ROL
 
; ROL8 (bit7 --> bit0)
CMP #$80
ROL
 
ASL
ADC #$0
 
; DoubleROL8 (bit7,6 --> bit1,0)
ASL
ADC #$80
ROL
 
; ROR8 (bit0 --> bit7)
LSR
BCC +2
ORA #$80
 
 
; Invert the bits of a byte
LDX #8
loop: 
ASL source
ROR
DEX
BNE loop
 
 
;  ASR (signed division by 2)
CMP #$80
ROR
 
 
; INV  (flip  .A)
EOR #$FF
 
 
; NEG  (-.A)
CLC
EOR #$FF
ADC #$01
 
SEC
EOR #$FF
ADC #$0
 
; NEG M  (-M)
SEC
LDA #$0
SBC M
 
;  Compare Sign
LDA N1
EOR N2
BPL SameSign
 
; Toggle  Carry
ROL
EOR #$01
ROR
 
ROR
EOR #$80
ROL
 

; copy bit7 of Memory into all bits (so it's $00 or $FF)
LDA #$7F
CMP Mem    ; Carry clear if >= $80
ADC #$80   ; $00 if carry set; $FF if carry clear


; copy carry into all bits
LDA #n
SBC #n
EOR #$FF


; Copy bit 3-5 of .A into M and leaving other untouched
EOR Mem
AND #$38   ; bits 3-5 (set the bits to be copied)
EOR Mem
STA Mem


; Copy bit 3-5 of M into .A
EOR Mem
AND #$C7   ; not bits 3-5
EOR Mem

 
;  Check if 16bit value is zero
LDA m
ORA m+1
BEQ iszero
 
;  Increment 16bit value
INC m
BNE skip
INC m+1
skip:
 
; Decrement 16bit value
LDA m
BNE skip
DEC m+1
skip: DEC m


; convert hex digit to ascii
SED
CMP #$0a
ADC #$30
CLD

CMP #$0A
BCC skip
ADC #$66    	; add $66+C; convert $0A to ascii
skip:
EOR #$30	; convert 00-09 to 30-39 and 71-76 to 41-46

CLC
SED
ADC #$90
ADC #$40
CLD

CLC
ADC #’0’
CMP #’9’+1
BCC skip
ADC #’A’-’0’-10-1
skip:


; is just 1 bit of .A set?
; (is .A a power of 2)
STA temp
DEC temp
BIT temp
BEQ IsPwrOf2


; indirect JSR
LDA #<dest
STA addr
LDA #>dest
STA addr+1
JSR (redirect)
...
redirect:
JMP(addr)

 
 
synthetic logical operators table
bit AND 0 = 0
bit OR 1 = 1
bit EOR 1 = not bit
User avatar
barrym95838
Posts: 2056
Joined: 30 Jun 2013
Location: Sacramento, CA, USA

Re: Old but Gold: in search for (forgotten) tricks

Post by barrym95838 »

Thanks for the kind mention, but I think I might have been inspired by some old Woz code. When I "upgraded" some of my code to CMOS, I also saved a byte on my complement carry (I didn't have anything useful in A at that moment):

Code: Select all

    rol a
    inc a
    ror a
I think David Galloway should be credited for the nyfty little nybble swap.
Got a kilobyte lying fallow in your 65xx's memory map? Sprinkle some VTL02C on it and see how it grows on you!

Mike B. (about me) (learning how to github)
barnacle
Posts: 1831
Joined: 19 Jan 2004
Location: Potsdam, DE
Contact:

Re: Old but Gold: in search for (forgotten) tricks

Post by barnacle »

I've used that trick on (heresy!) the 8080 (burn the witch!)

Neil :mrgreen:

edit: nah, can't have been... it has CMC. I wonder what it was, then?
User avatar
barrym95838
Posts: 2056
Joined: 30 Jun 2013
Location: Sacramento, CA, USA

Re: Old but Gold: in search for (forgotten) tricks

Post by barrym95838 »

Are accumulator bits 6 and 7 the same or different?

Code: Select all

    cmp #$C0    ; (thanks, Woz)
    bmi different
same:
    ...
different:
    ...
Useful while normalizing two's-complement floats. :wink:
Got a kilobyte lying fallow in your 65xx's memory map? Sprinkle some VTL02C on it and see how it grows on you!

Mike B. (about me) (learning how to github)
User avatar
barrym95838
Posts: 2056
Joined: 30 Jun 2013
Location: Sacramento, CA, USA

Re: Old but Gold: in search for (forgotten) tricks

Post by barrym95838 »

Code: Select all

;   Convert ASCII character to binary number in bases up to 41.
;   This translates A-Z[\]^_ and a-z{|}~DEL as 10, 11...40.
;   The caller must check the returned value if the intended base was
;   less than 41.
;
;          A: (written) ASCII character to convert; binary number on return
;     N flag: (written) clear on success, set on error.
;       X, Y: (preserved)
;
convascdigit
            cmp #'9'+1
            bcs .letter         ; >'9', convert letter
            sbc #'0'-1          ; convert digit; if <'0', N flag set for error
            rts                 ; N clear, no error
.letter
            and #%11011111      ; clear bit 5 to convert to upper-case
            bmi .exit           ; high bit set, error
            sbc #'A'-$0A
            cmp #$0A            ; if <$0A, set N flag to indicate error
.exit       rts
Courtesy of cjs.
Got a kilobyte lying fallow in your 65xx's memory map? Sprinkle some VTL02C on it and see how it grows on you!

Mike B. (about me) (learning how to github)
User avatar
barrym95838
Posts: 2056
Joined: 30 Jun 2013
Location: Sacramento, CA, USA

Re: Old but Gold: in search for (forgotten) tricks

Post by barrym95838 »

Code: Select all

{               } ; delay 9*(256*A+Y)+8 cycles
{               } ; assumes that the BCS does not cross a page boundary
{               } ;
{ 8000 C0 01    } .1 CPY # 1 ; 2
{ 8002 88       }    DEY     ; 2
{ 8003 E9 00    }    SBC # 0 ; 2
{ 8005 D0 F9    }    BCS =.1 ; 3
Courtesy of dclxvi.
Got a kilobyte lying fallow in your 65xx's memory map? Sprinkle some VTL02C on it and see how it grows on you!

Mike B. (about me) (learning how to github)
Post Reply