@ -0,0 +1,2 @@ | |||||
psxc | |||||
*.o |
@ -0,0 +1,15 @@ | |||||
CFLAGS ?= -Wall -Wextra -Iinclude | |||||
CFILES := $(shell find src -type f -name '*.c') | |||||
OFILES := $(CFILES:%.c=%.o) | |||||
.PHONY: clean | |||||
psxc: $(OFILES) | |||||
$(CC) $(OFILES) -o $@ | |||||
%.o: %.c | |||||
$(CC) $(CFLAGS) -c $< -o $@ | |||||
clean: | |||||
rm -f $(OFILES) psxc |
@ -0,0 +1,15 @@ | |||||
#ifndef PSXC_H_ | |||||
#define PSXC_H_ | |||||
#include <stdint.h> | |||||
#define SP(cpu) ((cpu)->regs[29]) | |||||
typedef struct { | |||||
uint32_t regs[32]; | |||||
uint32_t pc; | |||||
} cpu_t; | |||||
typedef void (*cpu_insn_handler)(cpu_t *, uint32_t); | |||||
#endif |
@ -0,0 +1,61 @@ | |||||
#ifndef PSXC_INSN_H_ | |||||
#define PSXC_INSN_H_ | |||||
#include <stdint.h> | |||||
typedef enum { | |||||
SPECIAL = 0x00, | |||||
BCONDZ = 0x01, | |||||
J = 0x02, | |||||
JAL = 0x03, | |||||
BEQ = 0x04, | |||||
BNE = 0x05, | |||||
BLEZ = 0x06, | |||||
BGTZ = 0x07, | |||||
ADDI = 0x08, | |||||
ADDIU = 0x09, | |||||
SLTI = 0x0a, | |||||
SLTIU = 0x0b, | |||||
ANDI = 0x0c, | |||||
ORI = 0x0d, | |||||
XORI = 0x0e, | |||||
LUI = 0x0f, | |||||
COP0 = 0x10, | |||||
COP1 = 0x11, | |||||
COP2 = 0x12, | |||||
COP3 = 0x13, | |||||
LB = 0x20, | |||||
LH = 0x21, | |||||
LWL = 0x22, | |||||
LW = 0x23, | |||||
LBU = 0x24, | |||||
LHU = 0x25, | |||||
LWR = 0x26, | |||||
SB = 0x28, | |||||
SH = 0x29, | |||||
SWL = 0x2a, | |||||
SW = 0x2b, | |||||
SWR = 0x2e, | |||||
LWC0 = 0x30, | |||||
LWC1 = 0x31, | |||||
LWC2 = 0x32, | |||||
LWC3 = 0x33, | |||||
SWC0 = 0x38, | |||||
SWC1 = 0x39, | |||||
SWC2 = 0x3a, | |||||
SWC3 = 0x3b, | |||||
} op_primary_t; | |||||
static inline op_primary_t extract_primary_op(uint32_t insn) { | |||||
return (insn >> 26) & 0x3f; | |||||
} | |||||
typedef enum { | |||||
SLL = 0x00, | |||||
} op_secondary_t; | |||||
static inline op_secondary_t extract_secondary_op(uint32_t insn) { | |||||
return (insn >> 0) & 0x3f; | |||||
} | |||||
#endif |
@ -0,0 +1,17 @@ | |||||
#include "cpu.h" | |||||
#include "insn.h" | |||||
static cpu_insn_handler primary_insn_handler[0x34] = {}; | |||||
static cpu_insn_handler secondary_insn_handler[0x34] = {}; | |||||
void cpu_execute_insn(cpu_t *cpu, uint32_t insn) { | |||||
const op_primary_t op = extract_primary_op(insn); | |||||
if (op == SPECIAL) { | |||||
const op_secondary_t op2 = extract_secondary_op(insn); | |||||
secondary_insn_handler[op2](cpu, insn); | |||||
return; | |||||
} | |||||
primary_insn_handler[op](cpu, insn); | |||||
} |
@ -0,0 +1 @@ | |||||
int main() { return 0; } |