summaryrefslogtreecommitdiff
path: root/usr.bin/oemu/cpu.c
diff options
context:
space:
mode:
Diffstat (limited to 'usr.bin/oemu/cpu.c')
-rw-r--r--usr.bin/oemu/cpu.c60
1 files changed, 59 insertions, 1 deletions
diff --git a/usr.bin/oemu/cpu.c b/usr.bin/oemu/cpu.c
index 49d4671..4aab553 100644
--- a/usr.bin/oemu/cpu.c
+++ b/usr.bin/oemu/cpu.c
@@ -187,6 +187,56 @@ cpu_mul(struct oemu_cpu *cpu, inst_t *inst)
printf("%d * %d -> X%d, new=%d\n",
imm, inst->imm, inst->rd, regs->xreg[inst->rd]);
}
+static void
+cpu_and(struct oemu_cpu *cpu, inst_t *inst)
+{
+ struct cpu_regs *regs = &cpu->regs;
+ imm_t imm;
+
+ if (inst->rd > NELEM(regs->xreg)) {
+ printf("bad register operand for 'and'\n");
+ return;
+ }
+
+ imm = inst->imm;
+ regs->xreg[inst->rd] &= inst->imm;
+ printf("X%d & %x -> X%d, new=%d\n",
+ inst->rd, inst->imm, inst->rd, regs->xreg[inst->rd]);
+}
+
+static void
+cpu_or(struct oemu_cpu *cpu, inst_t *inst)
+{
+ struct cpu_regs *regs = &cpu->regs;
+ imm_t imm;
+
+ if (inst->rd > NELEM(regs->xreg)) {
+ printf("bad register operand for 'or'\n");
+ return;
+ }
+
+ imm = inst->imm;
+ regs->xreg[inst->rd] |= imm;
+ printf("X%d | %x -> X%d, new=%d\n",
+ inst->rd, inst->imm, inst->rd, regs->xreg[inst->rd]);
+}
+
+static void
+cpu_xor(struct oemu_cpu *cpu, inst_t *inst)
+{
+ struct cpu_regs *regs = &cpu->regs;
+ imm_t imm;
+
+ if (inst->rd > NELEM(regs->xreg)) {
+ printf("bad register operand for 'xor'\n");
+ return;
+ }
+
+ imm = inst->imm;
+ regs->xreg[inst->rd] ^= imm;
+ printf("X%d ^ %x -> X%d, new=%d\n",
+ inst->rd, inst->imm, inst->rd, regs->xreg[inst->rd]);
+}
/*
* Decode the INST_DIV instruction
@@ -335,7 +385,6 @@ cpu_reset(struct oemu_cpu *cpu)
regs->ilr = 0x0;
memset(regs->xreg, 0x0, sizeof(regs->xreg));
}
-
void
cpu_regdump(struct oemu_cpu *cpu)
{
@@ -402,6 +451,15 @@ cpu_kick(struct oemu_cpu *cpu, struct sysmem *mem)
case INST_DIV:
cpu_div(cpu, inst);
break;
+ case INST_AND:
+ cpu_and(cpu, inst);
+ break;
+ case INST_OR:
+ cpu_or(cpu, inst);
+ break;
+ case INST_XOR:
+ cpu_xor(cpu, inst);
+ break;
case INST_BR:
cpu_br(cpu, inst);
break;