ref: 8a9c05b991899089f57ef6480d981b45e7489d57
dir: /5551e.c/
/* 5551 cpu emulator */ #include <stdbool.h> #include <stdio.h> #include "5551.h" typedef struct { bool flags[8]; int regs[8]; }reg_t; bool add_bit(bool a, bool b, bool *carry) { bool out, temp = *carry; out = ((a ^ b) ^ temp); *carry = (((a ^ b) & temp) | (a & b)); return out; } int main() { reg_t r; unsigned int memory[MMAX]; memory[MMAX-1] = -1; char string[16]; r.flags[ON] = 1; r.flags[NSIGN] = 0; unsigned int op, a, b, c; /* there is no space between op and args since some can have no args */ while(r.flags[ON] && scanf("%u %[^\n]", &op, string)) { sscanf(string, "%u %u %u", &a, &b, &c); switch(op) { case DIE: r.flags[ON] = 0; break; case OUT: /* just in case output is "manfi" */ if(r.flags[NSIGN]) printf("-%u\n", r.regs[a]); else printf("%u\n", r.regs[a]); break; case NOT: r.regs[b] = !a; break; case AND: r.regs[c] = a & b; break; case NOR: r.regs[c] = !(a | b); case XOR: r.regs[c] = a ^ b; break; case SUB: b = ~b; r.regs[CARRY] = 1; case ADD: r.regs[c] = add_bit(a, b, &r.flags[CARRY]); break; case SHR: r.regs[c] = r.regs[a] >> b; break; case SHL: r.regs[c] = r.regs[a] << b; break; case PUT: memory[b] = a; case MOV: memory[b] = r.regs[a]; break; case LDM: r.regs[b] = memory[a]; break; case NTH: r.regs[c] = a >> b; break; default: fprintf(stderr, "unkown op\n"); return 1; } /* clear them */ a = 0; b = 0; op = 0; string[0] = '\0'; } return 0; }