bit 1 | bit 2 | AND | OR | XOR | NOT |
---|---|---|---|---|---|
0 | 0 | 0 | 0 | 0 | 1 |
0 | 1 | 0 | 1 | 1 | |
1 | 0 | 0 | 1 | 1 | 0 |
1 | 1 | 1 | 1 | 0 |
%11110000 AND %01010101 %01010000 %11110000 OR %01010101 %11110101 %11110000 XOR %01010101 %10101010 NOT %11110000 %00001111
Naturally, the logical operations are available as Z80 instructions.
AND {reg8 | imm8 | (HL) } | Bitwise AND on the accumulator. | ||||||||
|
OR {reg8 | imm8 | (HL) } | Bitwise OR on the accumulator. | ||||||||
|
XOR {reg8 | imm8 | (HL) } | Bitwise exclusive OR on the accumulator. | ||||||||
|
CPL | Bitwise complement (NOT) of the accumulator. |
E.g. Use OR to force bits 1, 4, 5, and 7 to be set.
%00000000 %01100101 %10001111 OR %10110010 OR %10110010 OR %10110010 %10110010 %11110111 %10111111
E.g. Use AND to force bits 0, 1, 2, and 6 to be reset.
%11111111 %00111001 %01101101 AND %10111000 AND %10111000 AND %10111000 %10111000 %00111000 %00101000
E.g. Use XOR to flip bits 7 to 4.
%10101010 %11001100 %01011110 XOR %11110000 XOR %11110000 XOR %11110000 %01011010 %00111100 %10101110
Loop: DEC BC ; Update the counter LD A, B ; Load one half of the counter OR C ; Bitmask with the other half of the counter JR NZ, Loop ; If Z is reset then neither B or C is zero, so repeat
AND %00011111 ; A = A mod 32 AND %00000111 ; A = A mod 8
Loop: LD A, (count) INC A AND 2n-1 LD (count), A JP Z, Fishkill JR Loop
Instruction | Bytes | Cycles | Replacement | Bytes | Cycles | Downside |
---|---|---|---|---|---|---|
CP 0 | 2 | 7 | OR A / AND A | 1 | 4 | P/V flag is affected differently |
LD A, 0 | 2 | 7 | XOR A | 1 | 4 | Flags are affected SUB A will have the same effect, btw |
Sign | Overflow | Meaning |
---|---|---|
SET | SET | op1 >= op2 |
SET | CLEAR | op1 < op2 |
CLEAR | SET | op1 < op2 |
CLEAR | CLEAR | op1 >= op2 |
Interestingly, this looks just like the operation of XOR. So one could surmise that XORing the sign and overflow flags together after a comparison would yield their relationship.
Now, while it is impossible to do an operation on two flag bits, we can take advantage of the fact that the sign bit is a copy of the seventh bit of the result, then use an XOR bitmask if it's warranted. Although, this means that you have to use SUB instead of CP to do the comparison.
SUB -5 JP PO, $+5 ; P/V reset, and XORing with zero does nothing XOR $80 ; Can now use M for <, or P for >=
Be aware that this method does not leave the Z flag in any meaningful state.
SET n, {reg8 | (HL) } | Sets bit n (0-7) of the operand. |
RES n, {reg8 | (HL) } | Resets bit n (0-7) of the operand. |
BIT n, {reg8 | (HL) } | Checks bit n (0-7) of the operand. | ||||||||
|
There is a feature of the TI-OS called the system flags that you can take advantage of with these instructions. For starters, look at the Mode or Format menu. You'll see a bunch of options that affect graphing, trigonometry, numbers, etc. Each of these options is controlled by a system flag.
All the system flags are in an array with a base at $89F0, and the calculator has this address stored in IY. We can modify a system flag with the SET/RES instructions, and check them with the BIT instruction.
Example: This will check the trigonometric mode. If this bit is 1, then degree mode is set. If it's 0, radian mode is set.
BIT 2, (IY + 0) ; Checks bit 2 of byte $89F0What relates 2 and 0 to with trigonometry? Not much, the fact that this bit and byte combination record the trig setting was a completely arbitrary decision on TI's part. That's why all the bytes and offsets of the system flags are equated in the INC file:
BIT TrigDeg, (IY + TrigFlags)TrigDeg is equal to 2, and TrigFlags is equal to 0. This will do the same thing as above, but it's a lot easier to understand.