Introduction
Each row gives the instruction, the base opcode (the word with every operand field zero), its format, what it does and the
status bits it changes (L> A> EQ C OV OP X and the interrupt mask IM;
see the status register). Source and destination are
general operands. Operands are written source first, as in the TI assembler. Clock cycles
are not given: no readable source was found (see the overview).
The word counts: format I 1 to 3, formats III, IV, VI, IX 1 to 2, format VIII 1 to 2, the rest 1.
Two general operands (format I)
Bit 12 of the word makes the byte form (the name ends in B). A byte operand in a register is its high byte. The destination of every instruction except C and CB is changed (MOV does not read it as data, the others combine it with the source). MOV and MOVB read the destination before writing it; this matters only when the destination is a hardware address.
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
A | A000 | I | Add the source to the destination (word). | L> A> EQ C OV |
AB | B000 | I | Add bytes. OP is set for odd parity of the result byte. | L> A> EQ C OV OP |
C | 8000 | I | Compare the source with the destination (words); neither changes. | L> A> EQ |
CB | 9000 | I | Compare bytes. | L> A> EQ OP |
MOV | C000 | I | Move the source to the destination. | L> A> EQ |
MOVB | D000 | I | Move a byte. | L> A> EQ OP |
S | 6000 | I | Subtract the source from the destination. | L> A> EQ C OV |
SB | 7000 | I | Subtract bytes. | L> A> EQ C OV OP |
SOC | E000 | I | Set ones corresponding: destination = destination OR source. | L> A> EQ |
SOCB | F000 | I | As SOC for bytes. | L> A> EQ OP |
SZC | 4000 | I | Set zeros corresponding: destination = destination AND NOT source. | L> A> EQ |
SZCB | 5000 | I | As SZC for bytes. | L> A> EQ OP |
Jumps (format II)
Target = address of the jump + 2 + 2 × the signed displacement (−128 to +127 words). The assembler name NOP is the jump with displacement 0 (>1000); a displacement of −1 (>10FF) jumps to itself. The conditions: arithmetic compares use A>, logical compares L>.
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
JMP | 1000 | II | Jump always. | none |
JLT | 1100 | II | Jump if arithmetic less than: A> and EQ both clear. | none |
JLE | 1200 | II | Jump if logical low or equal: L> clear or EQ set. | none |
JEQ | 1300 | II | Jump if equal: EQ set. | none |
JHE | 1400 | II | Jump if logical high or equal: L> set or EQ set. | none |
JGT | 1500 | II | Jump if arithmetic greater than: A> set. | none |
JNE | 1600 | II | Jump if not equal: EQ clear. | none |
JNC | 1700 | II | Jump if no carry: C clear. | none |
JOC | 1800 | II | Jump on carry: C set. | none |
JNO | 1900 | II | Jump if no overflow: OV clear. | none |
JL | 1A00 | II | Jump if logical low: L> and EQ both clear. | none |
JH | 1B00 | II | Jump if logical high: L> set and EQ clear. | none |
JOP | 1C00 | II | Jump on odd parity: OP set. | none |
CRU instructions (formats II and IV)
The CRU (communications register unit) is a serial bit-addressed I/O space of 4096 bits. The base is R12 / 2; SBO, SBZ and TB add the signed displacement to it. LDCR and STCR transfer 1 to 16 bits starting at the base bit: a count C of 1 to 8 uses a byte operand, 9 to 15 and 0 (meaning 16) a word operand.
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
SBO | 1D00 | II | Set CRU bit R12 / 2 + displacement to one. | none |
SBZ | 1E00 | II | Set that bit to zero. | none |
TB | 1F00 | II | Test that bit: EQ is set if it is one. | EQ |
LDCR | 3000 | IV | Send C bits of the source to the CRU, least significant bit first. L> A> EQ describe the value sent; OP is set for byte counts. | L> A> EQ (OP for a byte count) |
STCR | 3400 | IV | Read C bits from the CRU into the destination (right-justified). | L> A> EQ (OP for a byte count) |
Register and general operand (format III)
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
COC | 2000 | III | Compare ones corresponding: EQ is set if every bit that is one in the source is one in the register. | EQ |
CZC | 2400 | III | Compare zeros corresponding: EQ is set if every bit that is one in the source is zero in the register. | EQ |
XOR | 2800 | III | Exclusive OR the source into the register. | L> A> EQ |
Extended operation, multiply and divide (format IX)
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
XOP | 2C00 | IX | Extended operation n (0 to 15): a context switch through the vector at >0040 + 4n; the source’s address goes in the new R11; the old WP, PC and ST in the new R13 to R15. | X |
MPY | 3800 | IX | Unsigned multiply of the register by the source: the high word in the register, the low word in the next. For R15 the next word is just beyond the workspace. | none |
DIV | 3C00 | IX | Unsigned divide of the 32-bit register pair by the source: quotient in the register, remainder in the next. If the source is not above the high word the quotient does not fit: OV is set and nothing is changed. | OV |
Shifts (format V)
The count is in the word (1 to 15); a count of 0 takes the count from the low four bits of R0, where 0 means 16.
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
SRA | 0800 | V | Shift right arithmetic: the sign bit is copied in; the last bit shifted out goes to C. | L> A> EQ C |
SRL | 0900 | V | Shift right logical: zeros come in. | L> A> EQ C |
SLA | 0A00 | V | Shift left arithmetic: OV is set if the sign bit changes during the shift. | L> A> EQ C OV |
SRC | 0B00 | V | Shift right circular: the bits shifted out come in at the left; C is the last one. | L> A> EQ C |
One general operand (format VI)
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
BLWP | 0400 | VI | Branch and load workspace pointer: the word at the operand’s address is the new WP, the next word the new PC; the old WP, PC and ST go in the new R13 to R15. | none |
B | 0440 | VI | Branch to the operand’s address. B *R11 is the return from a BL (assembler name RT). | none |
X | 0480 | VI | Execute the instruction in the operand; any extra words of that instruction are read from after the X itself. | those of the executed instruction |
CLR | 04C0 | VI | Clear the operand to zero. | none |
NEG | 0500 | VI | Negate (two’s complement). | L> A> EQ C OV |
INV | 0540 | VI | Invert all bits. | L> A> EQ |
INC | 0580 | VI | Add 1. | L> A> EQ C OV |
INCT | 05C0 | VI | Add 2. | L> A> EQ C OV |
DEC | 0600 | VI | Subtract 1. | L> A> EQ C OV |
DECT | 0640 | VI | Subtract 2. | L> A> EQ C OV |
BL | 0680 | VI | Branch and link: R11 gets the address of the next instruction, then branch to the operand’s address. | none |
SWPB | 06C0 | VI | Exchange the two bytes of the word. | none |
SETO | 0700 | VI | Set the operand to >FFFF. | none |
ABS | 0740 | VI | Absolute value (a negative operand is negated). The flags describe the operand before the change. | L> A> EQ C OV |
No operand (format VII)
The five external instructions put a code on the address bus (for hardware that watches it) and do nothing else on the chip; assemblers write the five unused low bits as zero.
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
IDLE | 0340 | VII | Stop executing until an interrupt or reset. | none |
RSET | 0360 | VII | Reset: clear the interrupt mask and send the RSET code. | IM |
RTWP | 0380 | VII | Return with workspace pointer: R13 to WP, R14 to PC, R15 to ST. | all (ST is loaded) |
CKON | 03A0 | VII | Clock on (external code). | none |
CKOF | 03C0 | VII | Clock off (external code). | none |
LREX | 03E0 | VII | Load or restart execution (external code). | none |
Immediate and register (format VIII)
All but STWP and STST are followed by a 16-bit immediate word.
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
LI | 0200 | VIII | Load the immediate into the register. | L> A> EQ |
AI | 0220 | VIII | Add the immediate to the register. | L> A> EQ C OV |
ANDI | 0240 | VIII | AND the immediate into the register. | L> A> EQ |
ORI | 0260 | VIII | OR the immediate into the register. | L> A> EQ |
CI | 0280 | VIII | Compare the register with the immediate. | L> A> EQ |
STWP | 02A0 | VIII | Store the workspace pointer in the register (no immediate word). | none |
STST | 02C0 | VIII | Store the status register in the register (no immediate word). | none |
LWPI | 02E0 | VIII | Load the workspace pointer from the immediate (the register field is unused). | none |
LIMI | 0300 | VIII | Load the interrupt mask from the low four bits of the immediate (the register field is unused). | IM |
TMS9995 additions
Decoded only when the TMS9995 variant is chosen; on the TMS9900 the words are Not in this ISA. These four rest on a recollection of the TMS9995 data manual and a list of mnemonics by model (Wikipedia); no core or readable table was available, so the opcodes and flags are unconfirmed.
| Instruction | Opcode | Format | What it does | Flags |
|---|---|---|---|---|
LST | 0080 | VIII | Load the status register from a register. | all (ST is loaded) |
LWP | 0090 | VIII | Load the workspace pointer from a register. | none |
DIVS | 0180 | VI | Signed divide of R0 and R1 by the operand: quotient in R0, remainder in R1. | OV |
MPYS | 01C0 | VI | Signed multiply of R0 by the operand: the 32-bit product in R0 and R1. | L> A> EQ |
Not described
Known, not yet covered
- Reference: clock cycles, memory accesses and wait states of each instruction.
- Reference: the exact flag results of the arithmetic instructions at the edges (NEG of >8000, ABS of >8000, SLA by 16) are described only in words.
Unknown
- Reference: the status flags of the TMS9995 additions; the C flag of ABS (the one core read always clears C for it; the table read lists C as changed).
- Reference: the flags published for SOCB and SRL in one table disagree with the other sources (it lists C for SOCB and OV for SRL); this page follows the data manual as remembered and the core.