summaryrefslogtreecommitdiff
path: root/sux.h
diff options
context:
space:
mode:
Diffstat (limited to 'sux.h')
-rw-r--r--sux.h68
1 files changed, 24 insertions, 44 deletions
diff --git a/sux.h b/sux.h
index 6ed0fc0..f3eb222 100644
--- a/sux.h
+++ b/sux.h
@@ -49,9 +49,7 @@ extern int get_key(WINDOW *scr);
extern void io(uint64_t address, uint8_t rw);
extern void init_scr();
-static inline uint64_t read_value(struct sux *cpu, uint64_t address, uint8_t size, uint8_t inc_clk, uint8_t check_io) {
- union reg value;
- value.u64 = 0;
+static inline uint64_t read_value(struct sux *cpu, uint64_t reg, uint64_t address, uint8_t size, uint8_t inc_clk, uint8_t check_io) {
#if (IO || debug) && !branch
#if keypoll
pthread_mutex_lock(&mutex);
@@ -63,33 +61,18 @@ static inline uint64_t read_value(struct sux *cpu, uint64_t address, uint8_t siz
pthread_mutex_unlock(&mutex);
#endif
#endif
- switch (size) {
- case 7: value.u8[7] = addr[address+7];
- case 6: value.u8[6] = addr[address+6];
- case 5: value.u8[5] = addr[address+5];
- case 4: value.u8[4] = addr[address+4];
- case 3: value.u8[3] = addr[address+3];
- case 2: value.u8[2] = addr[address+2];
- case 1: value.u8[1] = addr[address+1];
- case 0: value.u8[0] = addr[address+0];
- }
+ size = (size > 7) ? 7 : size;
+ uint64_t mask = (-(uint64_t)1 >> ((7 - size) * 8));
#if getclk
cpu->clk += inc_clk;
#endif
- return value.u64;
+ return (reg & ~mask) | (*(uint64_t *)(addr+address) & mask);
}
-static inline void write_value(struct sux *cpu, union reg value, uint64_t address, uint8_t size, uint8_t inc_clk, uint8_t check_io) {
- switch (size) {
- case 7: addr[address+7] = value.u8[7];
- case 6: addr[address+6] = value.u8[6];
- case 5: addr[address+5] = value.u8[5];
- case 4: addr[address+4] = value.u8[4];
- case 3: addr[address+3] = value.u8[3];
- case 2: addr[address+2] = value.u8[2];
- case 1: addr[address+1] = value.u8[1];
- case 0: addr[address+0] = value.u8[0];
- }
+static inline void write_value(struct sux *cpu, uint64_t value, uint64_t address, uint8_t size, uint8_t inc_clk, uint8_t check_io) {
+ size = (size > 7) ? 7 : size;
+ uint64_t mask = (-(uint64_t)1 >> ((7 - size) * 8));
+ *(uint64_t *)(addr+address) = (*(uint64_t *)(addr+address) & ~mask) | (value & mask);
#if (IO || debug) && !branch
#if keypoll
pthread_mutex_lock(&mutex);
@@ -135,9 +118,9 @@ static inline uint64_t read_addr(struct sux *cpu, uint8_t prefix, uint8_t inc_cl
uint64_t address;
uint8_t size = get_addrsize(prefix, type);
if (prefix >> 6) {
- address = offset_addr(cpu, read_value(cpu, cpu->pc, size, inc_clk, 0), size, inc_clk, prefix);
+ address = offset_addr(cpu, read_value(cpu, 0, cpu->pc, size, inc_clk, 0), size, inc_clk, prefix);
} else {
- address = read_value(cpu, cpu->pc, size, inc_clk, 0);
+ address = read_value(cpu, 0, cpu->pc, size, inc_clk, 0);
}
if (inc_pc) {
cpu->pc += size+1;
@@ -161,14 +144,14 @@ static inline uint64_t zmy_addr(struct sux *cpu, uint8_t prefix, uint8_t inc_clk
static inline uint64_t ind_addr(struct sux *cpu, uint8_t prefix, uint8_t inc_clk, uint8_t inc_pc) {
- return read_value(cpu, read_addr(cpu, prefix, inc_clk, ZM, inc_pc), 7, inc_clk, 0);
+ return read_value(cpu, 0, read_addr(cpu, prefix, inc_clk, ZM, inc_pc), 7, inc_clk, 0);
}
static inline uint64_t indx_addr(struct sux *cpu, uint8_t prefix, uint8_t inc_clk, uint8_t inc_pc) {
#if getclk
cpu->clk += inc_clk;
#endif
- return read_value(cpu, read_addr(cpu, prefix, inc_clk, ZM, inc_pc)+cpu->x, 7, inc_clk, 0);
+ return read_value(cpu, 0, read_addr(cpu, prefix, inc_clk, ZM, inc_pc)+cpu->x, 7, inc_clk, 0);
}
static inline uint64_t indy_addr(struct sux *cpu, uint8_t prefix, uint8_t inc_clk, uint8_t inc_pc) {
@@ -181,7 +164,7 @@ static inline uint64_t indy_addr(struct sux *cpu, uint8_t prefix, uint8_t inc_cl
static inline uint64_t rel_addr(struct sux *cpu, uint8_t prefix, uint8_t inc_clk, uint8_t inc_pc) {
uint8_t rs = (prefix >> 4) & 3;
uint8_t size = (1 << rs) - 1;
- uint64_t offset = read_value(cpu, cpu->pc, size, inc_clk, 0);
+ uint64_t offset = read_value(cpu, 0, cpu->pc, size, inc_clk, 0);
uint64_t address;
if (inc_pc) {
cpu->pc += (size + 1);
@@ -278,16 +261,14 @@ static inline void transfer(struct sux *cpu, uint64_t value, uint8_t opcode, uin
}
static inline void push(struct sux *cpu, uint64_t value, uint8_t size, uint8_t thread) {
- union reg reg;
- reg.u64 = value;
uint64_t sbr = (cpu->stk_st << 16);
- write_value(cpu, reg, (sbr+cpu->sp)-size, size, 1, 0);
+ write_value(cpu, value, (sbr+cpu->sp)-size, size, 1, 0);
cpu->sp -= size+1;
}
static inline uint64_t pull(struct sux *cpu, uint8_t size, uint8_t thread) {
uint64_t sbr = (cpu->stk_st << 16);
- uint64_t value = read_value(cpu, sbr+cpu->sp+1, size, 1, 0);
+ uint64_t value = read_value(cpu, 0, sbr+cpu->sp+1, size, 1, 0);
cpu->sp += size+1;
return value;
}
@@ -393,12 +374,12 @@ static inline uint64_t idr(struct sux *cpu, uint64_t reg, uint8_t inc, uint8_t t
/* Increment, or Decrement memory. */
static inline void idm(struct sux *cpu, uint64_t address, uint8_t prefix, uint8_t inc, uint8_t thread) {
uint8_t size = (1 << ((prefix >> 4) & 3))-1;
- union reg value;
- value.u64 = read_value(cpu, address, size, 1, 0);
+ uint64_t value;
+ value = read_value(cpu, 0, address, size, 1, 0);
if (inc) {
- value.u64++;
+ value++;
} else {
- value.u64--;
+ value--;
}
uint8_t sign = 0;
switch ((prefix >> 4) & 3) {
@@ -407,12 +388,13 @@ static inline void idm(struct sux *cpu, uint64_t address, uint8_t prefix, uint8_
case 2: sign = 31; break;
case 3: sign = 63; break;
}
- setflag(value.u64 == 0, Z);
- setflag(value.u64 >> sign, N);
+ setflag(value == 0, Z);
+ setflag(value >> sign, N);
write_value(cpu, value, address, size, 1, 1);
}
-static inline uint64_t load(struct sux *cpu, uint64_t value, uint8_t thread) {
+static inline uint64_t load(struct sux *cpu, uint64_t reg, uint64_t address, uint8_t size, uint8_t thread) {
+ uint64_t value = read_value(cpu, reg, address, size, 1, 1);
setflag(value == 0, Z);
setflag(value >> 63, N);
return value;
@@ -420,7 +402,5 @@ static inline uint64_t load(struct sux *cpu, uint64_t value, uint8_t thread) {
static inline void store(struct sux *cpu, uint64_t address, uint64_t reg, uint8_t prefix, uint8_t thread) {
uint8_t size = (1 << ((prefix >> 4) & 3))-1;
- union reg value;
- value.u64 = reg;
- write_value(cpu, value, address, size, 1, 1);
+ write_value(cpu, reg, address, size, 1, 1);
}