Question about AND

Discuss technical or other issues relating to programming the Nintendo Entertainment System, Famicom, or compatible systems.

Moderator: Moderators

Post Reply
User avatar
Sivak
Posts: 316
Joined: Tue Jul 17, 2007 9:04 am
Location: Somewhere
Contact:

Question about AND

Post by Sivak »

Alright. I know that in DOS assembly, you can use AND on a register to clear bits by having a binary mask of what you want cleared set to 0 and what you don't want cleared as 1. Then it stores the new number in the same register.

What I want to be able to do in 6502 is use an AND statement on something, use a mask to clear all but one bit. Say I want to look at bit #1 (mask of %00000010). Can I then take that bit I looked at and store its 1 or 0 into something or do I have to use a LSR and store after that?

Basically say I had a variable that had the binary value: %11111101, I loaded that into A and then performed AND with %00000010. Obviously bit #1 is 0. Can I take that 0 and store it without having to use a bunch of CMP statements?

Sorry if this sounds strange, but I tried wording it as best I could.
User avatar
blargg
Posts: 3717
Joined: Mon Sep 27, 2004 8:33 am
Location: Central Texas, USA
Contact:

Post by blargg »

Code: Select all

lda #%11111111
and #%00000010
sta flag
; flag = %00000010

lda #%00000000
and #%00000010
sta flag
; flag = %00000000
If you don't mind flag being 0 for false and %00000010 for true, then no LSR is needed. For example:

Code: Select all

lda flag
bne flag_is_true
flag_is_false:
...

flag_is_true:
...
Don't you have something you can run 6502 code with to try these things?
Last edited by blargg on Fri Dec 21, 2007 12:38 pm, edited 1 time in total.
tepples
Posts: 22345
Joined: Sun Sep 19, 2004 11:12 pm
Location: NE Indiana, USA (NTSC)
Contact:

Post by tepples »

Yes, you can store the result of an AND to memory.

Code: Select all

  ; prepare memory
  lda #%11111101
  sta $00
  lda #%11111111
  sta $01

  ; test AND instruction
  lda $00  ; A has %11111101
  and #%00000010  ; A has 00000000
  sta $02  ; $02 has 00000000

  lda $00  ; A has %11111111
  and #%00000010  ; A has 00000000
  sta $03  ; $03 has 00000010
Then when you load it back again, you can use BNE or BEQ to test whether the result was zero or nonzero:

Code: Select all

  lda $03
  beq dontRedraw
  jsr redrawLine
dontRedraw:
Celius
Posts: 2159
Joined: Sun Jun 05, 2005 2:04 pm
Location: Minneapolis, Minnesota, United States
Contact:

Post by Celius »

If you use many flags, which I'm sure you will, you may want to have 8 flags in a byte instead of just 1. It will take a few extra cycles to do AND before every comparison. So if you wanted to test bit #5, you'd have to do this:

Code: Select all

lda FlagHolder ;This byte holds 8 flags
and #$20 ; We test bit 5 by clearing all other bits except bit 5
beq FlagNotSet ;If the flag is not set, the value will be EQual to 0, so branch.
jsr FlagSet ;If the flag is set, the value will Not be Equal to 0, and will not branch, and it will come to here.
The only reason I say this is because the first minigame I made had me checking for flags, and I only used the first bit of every bit to determine if a flag was set. The code was ugly, sloppy, and a terrible space-waster.
Post Reply