Initial commit

This commit is contained in:
attilavs2 2024-07-27 21:49:56 +02:00
commit 5a5bed307d
7 changed files with 1014 additions and 0 deletions

2
assembl/Makefile Normal file
View file

@ -0,0 +1,2 @@
[all]:
gcc src/main.c -lm

BIN
assembl/a.out Executable file

Binary file not shown.

254
assembl/src/main.c Normal file
View file

@ -0,0 +1,254 @@
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <stdint.h>
typedef struct{
int id;
int ntyps;
//Bitfields representing possible arg combinations:
//(Using left to right big endian naming)
// upper 4 bits : left arg / arg1
// lower 4 bits : right arg / arg2
//0 : rm/rn
//1 : r0
//2 : *rm/*rn
//3 : #imm
//4 : *#imm
//5 : sr
//6 : *sr
//7 : sr0-1
//F : none
uint8_t argtyps[7];
//Opcodes for the different types, a 0xF
//nibble indicates replaceable
uint16_t opcodes[7];
} InstrDef;
#define INSTR_DICT_S 29
InstrDef instr_dict[INSTR_DICT_S] = {
{0 ,1, {0xFF,0,0,0,0,0,0},{0,0,0,0,0,0,0}},//nop
{1 ,7, {0x00,0x03,0x02,0x04,0x20,0x40,0x22},{0x20FF,0x8FFF,0xB0FF,0x9FFF,0xB1FF,0xAFFF,0xB2FF}},//mov
{2 ,2, {0x06,0x60,0,0,0,0,0},{0xB3FF,0xB4FF,0,0,0,0,0}},//mmv
{3 ,1, {0x0F,0,0,0,0,0,0},{0xB5F0,0,0,0,0,0,0}},//psh
{4 ,1, {0x0F,0,0,0,0,0,0},{0xB6F0,0,0,0,0,0,0}},//pop
{5 ,1, {0x70,0,0,0,0,0,0},{0xE0FF,0,0,0,0,0,0}},//lds
{6 ,1, {0x07,0,0,0,0,0,0},{0xE1FF,0,0,0,0,0,0}},//sts
{7 ,2, {0x00,0x13,0,0,0,0,0},{0x40FF,0x48FF,0,0,0,0,0}},//add
{8 ,1, {0x70,0,0,0,0,0,0},{0xE2FF,0,0,0,0,0,0}},//sad
{9 ,1, {0x00,0,0,0,0,0,0},{0x41FF,0,0,0,0,0,0}},//sub
{10,1, {0x0F,0,0,0,0,0,0},{0x42F0,0,0,0,0,0,0}},//shl
{11,1, {0x0F,0,0,0,0,0,0},{0x43F0,0,0,0,0,0,0}},//shr
{12,1, {0x00,0,0,0,0,0,0},{0x44FF,0,0,0,0,0,0}},//and
{13,1, {0x00,0,0,0,0,0,0},{0x45FF,0,0,0,0,0,0}},//or
{14,1, {0x00,0,0,0,0,0,0},{0x46FF,0,0,0,0,0,0}},//xor
{15,1, {0x0F,0,0,0,0,0,0},{0x47FF,0,0,0,0,0,0}},//not
{16,1, {0xFF,0,0,0,0,0,0},{0x6000,0,0,0,0,0,0}},//rtb
{17,1, {0x00,0,0,0,0,0,0},{0x61FF,0,0,0,0,0,0}},//gth
{18,1, {0x00,0,0,0,0,0,0},{0x64FF,0,0,0,0,0,0}},//gts
{19,1, {0x00,0,0,0,0,0,0},{0x62FF,0,0,0,0,0,0}},//eql
{20,1, {0x0F,0,0,0,0,0,0},{0x63F0,0,0,0,0,0,0}},//stb
{21,2, {0x2F,0x4F,0,0,0,0,0},{0x32F0,0x30FF,0,0,0,0,0}},//br
{22,2, {0x2F,0x4F,0,0,0,0,0},{0x35F0,0x31FF,0,0,0,0,0}},//bt
{23,1, {0x2F,0,0,0,0,0,0},{0x33F0,0,0,0,0,0,0}},//bf
{24,1, {0x6F,0,0,0,0,0,0},{0x34F0,0,0,0,0,0,0}},//jmp
{25,1, {0x0F,0,0,0,0,0,0},{0x71F0,0,0,0,0,0,0}},//itp
{26,1, {0xFF,0,0,0,0,0,0},{0x7200,0,0,0,0,0,0}},//dsi
{27,1, {0xFF,0,0,0,0,0,0},{0x7300,0,0,0,0,0,0}},//eni
{28,1, {0x0F,0,0,0,0,0,0},{0x70F0,0,0,0,0,0,0}}//rgi
};
char *instr_tok_dict[INSTR_DICT_S] = {
"nop",
"mov",
"mmv",
"psh",
"pop",
"lds",
"sts",
"add",
"sad",
"sub",
"shl",
"shr",
"and",
"or",
"xor",
"not",
"rtb",
"gth",
"gts",
"eql",
"stb",
"br",
"bt",
"bf",
"jmp",
"itp",
"dsi",
"eni",
"rgi"
};
int find_token(char *token, int dicts, char *dict[]){
int toklen = strlen(token);
if(toklen < 2) return -1;
for(int i=0; i < dicts; i++){
if(token[1] == dict[i][1]){
if(!strcmp(token, dict[i])){
return i;
}
}
}
return -1;
}
int uint8_t_cmpfunc(const void *a, const void *b){
return *(uint8_t*)a - *(uint8_t*)b;
}
int find_corres_def(uint8_t argtyps, InstrDef *indef){
uint8_t *match = bsearch(&argtyps, &indef->argtyps, 7, 1, &uint8_t_cmpfunc);
if(!match) return -1;
return (int64_t)match - (int64_t)&indef->argtyps;
}
int32_t pars_line(char *line){
char *tok;
tok = strtok(line, " ");
int tokid = find_token(tok, INSTR_DICT_S, instr_tok_dict);
if(tokid < 0) return -1;
InstrDef *indef = &instr_dict[tokid];
tok = strtok(NULL, " ");
char *ntok = strtok(NULL, " ");
tok = strtok(tok, ",");
int8_t argtyps = 0xFF;
int8_t argt[2] = {0xF,0xF};
int8_t fargs[2];
int8_t rn, imm;
for(int i = 0; i < 2; i++){
if(!strncmp(tok,"ac",2) + (!strncmp(tok,"pc",2))*2 && strlen(tok)>2){
if((tok[2]-48) > -1 && (tok[2]-48) < 10){
argt[i] = 0x7;
fargs[i] = !strncmp(tok,"ac",2) + (!strncmp(tok,"pc",2))*2 + tok[2]-48;
}
}
if(!strncmp(tok,"*ac",2) + (!strncmp(tok,"*pc",2))*2){
argt[i] = 0x6;
fargs[i] = !strncmp(tok,"*ac",2) + (!strncmp(tok,"*pc",2))*2;
}
if(strlen(tok)>1 && !strncmp(tok,"r",1)){
if(!sscanf(&tok[1], "%d", &rn)){
return -2;
}
else if(rn > -1 && rn < 16){
argt[i] = 0x0;
fargs[i] = rn;
}
else {
return -2;
}
}
if(strlen(tok)>1 && !strncmp(tok,"*r",1)){
if(!sscanf(&tok[2], "%d", &rn)){
return -2;
}
if(rn > -1 && rn < 16){
argt[i] = 0x2;
fargs[i] = rn;
}
else return -2;
}
if(strlen(tok)>1 && !strncmp(tok, "#",1)){
if(!sscanf(&tok[1], "%d", &imm)){
return -2;
}
if(imm < -128 || imm > 127){
return -3;
}
argt[i] = 0x3;
fargs[i] = imm;
}
if(strlen(tok) > 1 && !strncmp(tok,"*#",2)){
if(!sscanf(&tok[2], "%d", &imm)){
return -2;
}
if(imm < -128 || imm > 127){
return -3;
}
argt[i] = 0x4;
fargs[i] = imm;
}
tok = ntok;
argtyps = (argtyps & (0xF0F>>(i*4)));
argtyps += (argt[i] << (4-i*4));
}
int instt = find_corres_def(argtyps, indef);
if(instt < 0) return -4;
uint16_t op = indef->opcodes[instt];
uint8_t *opb = &op;
if((argtyps & 0xF0) < 5 && (argtyps & 0xF0) > 2){
opb[1] = (opb[1] & 0x0F) + fargs[1];
opb[0] = fargs[0];
return op;
}
if((argtyps & 0x0F) < 5 && (argtyps & 0x0F) > 2){
opb[1] = (opb[1] & 0xF0) + fargs[0];
opb[0] = fargs[1];
return op;
}
if((argtyps & 0xF0) < 3 || (argtyps & 0xF0 > 4 && argtyps & 0xF0 < 8)){
opb[1] = opb[1] & 0x0F + fargs[0];
}
if(argtyps & 0x0F < 3 || (argtyps & 0x0F > 4 && argtyps & 0x0F < 8)){
opb[1] = opb[1] & 0xF0 + fargs[1];
}
return op;
}
int main(int argc, int *argv[]){
if(argc < 2) return -1;
char *line_ = argv[1];
char *line = malloc(strlen(line_));
memcpy(line, line_, 11);
printf("%x\n", pars_line(line));
return 0;
}

5
interpr/Makefile Normal file
View file

@ -0,0 +1,5 @@
CFLAGS = -O2 -lm
CC = gcc
[all]:
${CC} src/main.c ${CFLAGS}

BIN
interpr/a.out Executable file

Binary file not shown.

421
interpr/src/main.c Normal file
View file

@ -0,0 +1,421 @@
#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <string.h>
#define MEM_ALLOC 0xFFFF //64KiB
#define TOTAL_ALLOC (MEM_ALLOC)
#define BOOTCODE_S 18
uint8_t bootcode[] = {
0x00,0xFF,
0xFF,0x00,
0x00,0x06,
0x72,0x00,
0xB6,0xE0,
0xE0,0x0E,
0xB6,0xE0,
0xE0,0x1E,
0x34,0x00
};
typedef struct{
uint8_t *mem;
uint8_t greg[16];
uint16_t sreg[2];
uint8_t interr[16];
uint8_t intern;
uint8_t interen;
uint8_t tbit;
int32_t cycles;
} ProcDat;
int init_proc(ProcDat *procdat){
procdat->mem = malloc(MEM_ALLOC);
if(!procdat->mem){
return 1;
}
for(int i=0; i<BOOTCODE_S; i++){
procdat->mem[i] = bootcode[i-1];
}
for(int i=BOOTCODE_S; i<MEM_ALLOC; i++){
procdat->mem[i] = 1;
}
procdat->sreg[1] = procdat->mem[0]<<8 + procdat->mem[1];
printf("%x\n", procdat->mem[1]);
procdat->interen = 1;
procdat->interr[0] = 0b01;
procdat->intern = 1;
procdat->cycles = 0;
return 0;
}
void free_proc(ProcDat *procdat){
free(procdat->mem);
}
void itp(uint8_t interrupt, uint8_t call_type, ProcDat *procdat){
if(!procdat->interen)return;
if(!(procdat->interr[interrupt] & 0x2) && call_type) return;
printf("Interrupt %x, PC : %x\n", interrupt, procdat->sreg[1]);
uint16_t st = procdat->mem[0x2]<<8 + procdat->mem[0x3];
procdat->mem[st+procdat->greg[12]] = procdat->sreg[1] >> 8;
procdat->greg[12]++;
procdat->mem[st+procdat->greg[12]] = procdat->sreg[1] & 0xFF;
procdat->greg[12]++;
procdat->sreg[1] = procdat->mem[3]<<8 + procdat->mem[4];
}
int exec_instr(uint16_t instr, ProcDat *procdat){
int8_t in0 = instr & 0xFF;
uint8_t in1 = instr & 0xF;
uint8_t in2 = (instr>>4) & 0xF;
uint8_t in3 = (instr>>8) & 0xF;
uint8_t in4 = instr>>12;
uint8_t *greg = &procdat->greg;
uint16_t *sreg = &procdat->sreg;
uint8_t *mem = procdat->mem;
uint16_t st = mem[0x2]<<8 + mem[0x3];
int32_t cycles = 0;
switch(in4){
case 0x2 : {
greg[in2] = greg[in1];
cycles++;
break;
}
case 0x3 : {
switch(in3){
case 0x0 : {
sreg[1] += in0*2;
cycles++;
break;
}
case 0x1 : {
if(procdat->tbit){
sreg[1] += in0*2;
}
cycles++;
break;
}
case 0x2 : {
sreg[1] += ((int8_t)in2)*2;
cycles++;
break;
}
case 0x3 : {
if(!procdat->tbit){
sreg[1] += ((int8_t)in2)*2;
}
cycles++;
break;
}
case 0x4 : {
sreg[1] = sreg[0];
cycles+=2;
break;
}
case 0x5 : {
if(procdat->tbit){
sreg[1] += ((int8_t)in2)*2;
}
cycles++;
break;
}
default : {
itp(0, 0, procdat);
break;
}
}
}
case 0x4 : {
switch(in3){
case 0x0 : {
greg[in2] += greg[in1];
cycles++;
break;
}
case 0x1 : {
greg[in2] -= greg[in1];
cycles++;
break;
}
case 0x2 : {
greg[in2] <<= 1;
cycles++;
break;
}
case 0x3 : {
greg[in2] >>= 2;
cycles++;
break;
}
case 0x4 : {
greg[in2] &= greg[in1];
cycles++;
break;
}
case 0x5 : {
greg[in2] |= greg[in1];
cycles++;
break;
}
case 0x6 : {
greg[in2] ^= greg[in1];
cycles++;
break;
}
case 0x7 : {
greg[in2] = ~greg[in2];
cycles++;
break;
}
case 0x8 : {
greg[0] += in0;
cycles++;
break;
}
default : {
itp(0, 0, procdat);
break;
}
}
break;
}
case 0x6 : {
switch(in3){
case 0x0 : {
procdat->tbit = 0;
cycles++;
break;
}
case 0x1 : {
procdat->tbit = greg[in2] > greg[in1];
cycles++;
break;
}
case 0x2 : {
procdat->tbit = greg[in2] == greg[in1];
cycles++;
break;
}
case 0x3 : {
greg[in2] = procdat->tbit;
cycles++;
break;
}
case 0x4 : {
procdat->tbit = (int8_t)greg[in2] > (int8_t)greg[in1];
cycles++;
break;
}
default : {
itp(0, 0, procdat);
break;
}
}
break;
}
case 0x7 : {
switch(in3){
case 0x0 : {
if(procdat->intern > 15){
greg[in2] = 0xFF;
break;
}
procdat->interr[procdat->intern] = greg[in2];
procdat->intern++;
cycles+=2;
break;
}
case 0x1 : {
itp(in2, 1, procdat);
cycles+=6;
break;
}
case 0x2 : {
procdat->interen = 0;
printf("PC : %x - disabled interrupts\n", sreg[1]);
cycles++;
break;
}
case 0x3 : {
procdat->interen = 1;
printf("PC : %x - enabled interrupts\n", sreg[1]);
cycles++;
break;
}
default : {
itp(0, 0, procdat);
break;
}
}
}
case 0x8 : {
greg[in3] = in0;
cycles++;
break;
}
case 0x9 : {
greg[in3] = mem[(sreg[1]+in0)&0xFFFF];
cycles++;
break;
}
case 0xA : {
mem[(sreg[1]+in0)&0xFFFF] = greg[in3];
cycles++;
break;
}
case 0xB : {
switch(in3){
case 0x0 : {
greg[in2] = mem[(sreg[1]+(int8_t)greg[in1])&0xFFFF];
cycles++;
break;
}
case 0x1 : {
mem[(sreg[1]+(int8_t)greg[in2])&0xFFFF] = greg[in1];
cycles++;
break;
}
case 0x2 : {
mem[(sreg[1]+(int8_t)greg[in2])&0xFFFF] = mem[(sreg[1]+(int8_t)greg[in1])&0xFFFF];
cycles++;
break;
}
case 0x3 : {
greg[in2] = mem[sreg[0]];
cycles++;
break;
}
case 0x4 : {
mem[sreg[0]] = greg[in1];
cycles++;
break;
}
case 0x5 : {
mem[st+greg[12]] = greg[in2];
greg[12]++;
cycles+=2;
break;
}
case 0x6 : {
greg[12]--;
greg[in2] = mem[st+greg[12]];
cycles+=2;
break;
}
default : {
itp(0, 0, procdat);
break;
}
}
break;
}
case 0xE : {
switch(in3){
case 0x0 : {
if(in2 < 2){
sreg[1] = (sreg[1] & (0x00FF00>>(8*in2))) + greg[in1]<<(8*in2);
}
cycles++;
break;
}
case 0x1 : {
greg[in2] = sreg[in1/2] >> (in1%2 ? 8:0);
cycles++;
break;
}
case 0x2 : {
sreg[in2] += greg[in1];
cycles++;
break;
}
default : {
itp(0, 0, procdat);
break;
}
}
break;
}
default : {
itp(0, 0, procdat);
break;
}
}
sreg[1]+=2;
procdat->cycles += cycles;
if(mem[sreg[1]] == 1){
return 0;
}
if(mem[sreg[1]])
return 1;
}
int main(){
ProcDat procdat;
if(init_proc(&procdat)){
printf("Error during initialization !\n(Likely couldn't allocate %d KiB)\n", TOTAL_ALLOC/1024);
free_proc(&procdat);
return 1;
}
char *buf = malloc(100);
while(1){
int inp = 0;
int i;
scanf("%X", &inp);
if(inp == 0x1){
scanf("%99s", buf);
if(!memcmp(buf, "-d", 2)){
printf("PC : %x AC : %x\n", procdat.sreg[1], procdat.sreg[0]);
for(i=0; i<16; i++){
printf("r%d : %x\n", i, procdat.greg[i]);
}
for(i=0; i<MEM_ALLOC;){
printf("%x : ", i);
i++;
printf("%x ",procdat.mem[i]);
i++;
printf("%x\n",procdat.mem[i]);
}
}
if(!memcmp(buf, "-q", 2)){
break;
}
}
else{
if(exec_instr(inp & 0xFFFF, &procdat)){
while(exec_instr(procdat.mem[procdat.sreg[1]], &procdat)){}
}
}
}
exit:
free_proc(&procdat);
return 0;
}

332
spec.txt Normal file
View file

@ -0,0 +1,332 @@
instruction format:
big endian
16bits
Bit order:
0 : Largest (leftmost), 7 : smallest (rightmost)
registers:
r0-r12 (mov 0x0-0xc):
general purpose
8 bits
r13-r15 (mov 0xd-0xf):
Interrupt reserved
8 bits
ac,pr (special 0x0,1):
accumulator, progam counter
16bits
ac0-1,pc0-1 (lds/sts 0x0-1,0x2-3):
accumulator, progam counter
8-8bits (lower-upper)
id (special 0x2):
interrupt data,
set by the interrupt
if raised by bus
8bits
in (Special 0x3):
interrupt register,
contains the type of
interrupt
4bits - bits 0-3 will always be 0
t bit:
is set by comp ops
1bit
calling conventions:
r0-r1 : return registers
r2-r11: call args
r12 : stack pos
r13-15:interrupt reserved (only adressable in interrupt mode)
caller pushes desired return addr
to stack, callee jumps to it
Interrupts:
Hardware interrupts:
0x0 : Invalid instruction
The 15 other interrupts are free to
define by the user
On interrupt (either called through
the bus or itp)
startup:
the cpu will look
at adress 0x0,and
expects to find :
-0x0-1: adress of
the starting
point,will be
jumped to
-0x2-3: adress of
the stack, the
adress will be
read here
everytime
-0x4-5:adress of
the interrupt
handler, the
adress will be
read here
everytime
When an interrupt is raised, the cpu will allow acces
to r12-15 and push the resume adress to stack (in
order pc0 then pc1)
instructions :
format:
rm,rn: general purpose registers
#imm:immediate signed 8bit value
*rm:memory at adress (pc+rm)
*#imm:memory at adress (pc+#imm)
sr: pr,ac
sr0-1: pr0-1/ac0-1, in/id
st: stack adress that is at 0x2,
abreviation for explanation only
nop :
0b0000000000000000
0x0000
No-OP:
Does nothing
1 clock
mov rm,rn:
0b00100000mmmmnnnn
0x20mn
MOVe :
rm <- rn
1 clock
mov rn,#imm:
0b1000nnnnmmmmmmmm
0x8nmm
rn <- #imm
1 clock
mov rm,*rn:
0b11000000mmmmnnnn
0xB0mn
rm <- *(pc+rn)
1 clock
mov rn,*#imm:
0b1001nnnnmmmmmmmm
0x9nmm
rn <- *(pc+#imm)
1 clock
mov *rm,rn:
0b11000001mmmmnnnn
0xB1mn
*(pc+rm) <- rn
1 clock
mov *#imm,rn:
0b1010nnnnmmmmmmmm
0xAnmm
*(pc+#imm) <- rn
1 clock
mov *rm,*rn:
0b11000010mmmmnnnn
0xB2mn
*(pc+rm) <- *(pc+rn)
1 clock
mmv rm, *sr:
0b11000011mmmmssss
0xB3ms
Memory MoVe
rm <- *sr
Meant to be used with the accumulator
1 clock
mmv *sr, rm:
0b11000100ssssmmmm
0xB4sm
*sr <- rm
Meant to be used with the accumulator
1 clock
psh rm:
0b11000101mmmm0000
0xB5m0
PuSH to stack:
*(st+r11) <- rm
r11 <- r11+1
2 clocks
pop rm:
0b11000110mmmm0000
0xB6m0
POP from stack
r11 <- r11-1
rm <- *(st+r11)
2 clocks
lds sr0-1,rm:
0b11100000ssssmmmm
0xE0sm
LoaD Special :
sr0-1 <- rm
nop on pc
1 clock
sts rm,sr0-1:
0b11100001mmmmssss
0xE1ms
STore Special :
rm <- sr0-1
1 clock
add rn,rm:
0b01000000nnnnmmmm
0x40nm
ADD :
rn <- rn+rm
1 clock
add r0,#imm:
0b01001000mmmmmmmm
0x48mm
r0 <- r0+#imm
1 clock
sad sr0-1,rm:
0b11100010ssssmmmm
0xE2sm
Special ADd
sr0-1 <- sr0-1+rm
(16bit add)
nop on pc
1 clock
sub rm,rn:
0b01000001mmmmnnnn
0x41mn
SUBstract :
rm <- rm-rn
1 clock
shl rm:
0b01000010mmmm0000
0x42m0
SHift Left
rm <- rm<<1
pure shift, no keep sign
1 clock
shr rm:
0b01000011mmmm0000
0x43m0
SHift Right
rm <- rm>>1
pure shift, no keep sign
1 clock
and rm,rn:
0b01000100mmmmnnnn
0x44mn
binary AND :
rm <- rm&rn
1 clock
or rm,rn:
0b01000101mmmmnnnn
0x45mn
binary OR :
rm <- rm|rn
1 clock
xor rm,rn:
0b01000110mmmmnnnn
0x46mn
binary eXclusive OR:
rm <- rm^rn
1 clock
not rm:
0b01000111mmmmnnnn
0x47mn
binary NOT :
rm <- !rm
binary not
1 clock
rtb :
0b0110000000000000
0x6000
Reset T Bit :
t <- 0
1 clock
gth rm,rn:
0b01100001mmmmnnnn
0x61mn
Greater THan :
t <- rm > rn ? 1:0
1 clock
gts rm,rn:
0b01100100mmmmnnn
0x64mn
Greater Than (Signed):
t <- rm > rn ? 1:0
(signed) (signed)
1 clock
eql rm,rn:
0b01100010mmmmnnnn
0x62mn
EQuaL :
t <- rm == rn ? 1:0
1 clock
stb rm:
0b01100011mmmm0000
0x63m0
Store T Bit:
rm <- t
1 clock
br *rm:
0b10110010mmmm0000
0x32m0
BRanch :
pc <- pc + rm *2
(signed)
1 clock
br *#imm:
0b10110000mmmmmmmm
0x30mm
pc <- pc + #imm*2
1 clock
bt *rm:
0b10110101mmmm0000
0x35m0
Branch if True:
If t == 1,
pc <- pc + rm *2
(signed)
else is nop
1 clock
bt *#imm:
0b10110001mmmmmmmm
0x31mm
If t == 1,
pc <- pc + #imm*2
else is nop
1 clock
bf *rm:
0b10110011mmmm0000
0x33m0
Branch if False:
If t == 0,
pc <- pc + rm *2
(signed)
else is nop
1 clock
jmp *sr:
0b10110100ssss0000
0x34s0
JuMP :
pc <- sr
nop on pc
2 clocks
itp rm:
0b01110001mmmm0000
0x71m0
InTerruPt :
Raises interrupt of id
rm
6 clocks
dsi :
0b0111001000000000
0x7200
DiSable Interrupts:
Disables interrupts
1 clock
eni :
0b0111001100000000
0x7300
ENable Interrupts:
Enables interrupts
1 clock
rgi rm:
0b01110000mmmm0000
0x70m0
ReGister Interrupt :
rm should be as follows:
bit 0 : raisable by itp
bit 1 : raisable by bus
Sets rm to id on succes,
and 0xFF on failure
2 clocks