diff options
| author | Louis Burda <quent.burda@gmail.com> | 2023-12-25 03:08:10 +0100 |
|---|---|---|
| committer | Louis Burda <quent.burda@gmail.com> | 2023-12-25 03:08:10 +0100 |
| commit | ae4a7b241a033627ed136b2ef66922034cfbeae1 (patch) | |
| tree | e8f045d51a36c2f9c24b63d962bcf84baebdc3c9 /tpu.c | |
| parent | f2ada47e6be185cc31c475c996c4ccf6735f7bb0 (diff) | |
| download | tis100-ae4a7b241a033627ed136b2ef66922034cfbeae1.tar.gz tis100-ae4a7b241a033627ed136b2ef66922034cfbeae1.zip | |
Add more fixes for game compatibility
Diffstat (limited to 'tpu.c')
| -rw-r--r-- | tpu.c | 45 |
1 files changed, 24 insertions, 21 deletions
@@ -137,7 +137,6 @@ tpu_port_init(struct tpu_port *port, struct tpu *tpu) port->dst_port = NULL; port->type = PORT_BIDI; port->reset_in = false; - port->reading = false; port->writing = false; port->avail = false; port->in = -1; @@ -166,13 +165,14 @@ tpu_port_update(struct tpu_port *port) if (port->reset_in && (!port->tpu || !port->tpu->idle)) { port->avail = false; port->dst_port->writing = false; - port->reset_in = false; if ((tpu = port->dst_port->tpu)) { - /* hacky: only allow mode to be RUN after receive */ + /* hacky: switch mode to RUN after receive */ + assert(tpu->mode == MODE_WRITE); tpu->mode = MODE_RUN; tpu->idle = false; if (++tpu->pc >= tpu->inst_cnt) tpu->pc = 0; } + port->reset_in = false; } } @@ -352,18 +352,16 @@ tpu_add_inst(struct tpu *tpu, enum tpu_inst_type inst_type, return &tpu->insts[tpu->inst_cnt++]; } -/* tpu can only read values if there is a writer attached and offering a - * value (->dst_port->out) -- which is cleared on successful read */ +/* tpu can only read values if there is a writer attached and offering + * a value -- this value is cleared on successful read */ static bool tpu_port_read(struct tpu *tpu, enum tpu_port_dir dir, int *lit) { struct tpu_port *port = &tpu->ports[dir]; - if (!port->avail) { - port->reading = true; + if (!port->avail) return false; - } *lit = port->in; port->reset_in = true; @@ -371,23 +369,20 @@ tpu_port_read(struct tpu *tpu, enum tpu_port_dir dir, int *lit) return true; } -/* tpu can always write values (->out) but only finish writing once the - * written value is read and cleared by the reader (->dst_port->in) */ +/* tpu can write value to ->out immediately but only finish the instruction + * once the written value is read and cleared by the reader */ static bool tpu_port_write(struct tpu *tpu, enum tpu_port_dir dir, int lit) { struct tpu_port *port = &tpu->ports[dir]; - if (port->writing) { + if (port->writing) return false; - } port->writing = true; port->out = lit; - /* port writing never succeeds right away, only after - * value was read in tpu_update is tpu->idle/mode fixed up */ return true; } @@ -473,16 +468,21 @@ tpu_exec(struct tpu *tpu, struct tpu_inst *inst) tpu->pc += 1; return MODE_RUN; case INST_MOV: - if (tpu->mode != MODE_WRITE) { - if (!tpu_exec_get(tpu, &inst->ops[0], &lit)) { - tpu->idle = true; - return MODE_READ; - } + if (tpu->mode == MODE_WRITE) { + tpu->idle = true; + return MODE_WRITE; + } + if (!tpu_exec_get(tpu, &inst->ops[0], &lit)) { + tpu->idle = true; + return MODE_READ; } if (!tpu_exec_put(tpu, &inst->ops[1], lit)) { tpu->idle = true; return MODE_WRITE; } + /* if MOV to port, set WRITE tentatively and fix on reset_in */ + if (inst->ops[1].type != OP_ACC && inst->ops[1].type != OP_NIL) + return MODE_WRITE; tpu->pc += 1; return MODE_RUN; case INST_SWP: @@ -504,8 +504,10 @@ tpu_exec(struct tpu *tpu, struct tpu_inst *inst) tpu->pc += 1; return MODE_RUN; case INST_SUB: - if (!tpu_exec_get(tpu, &inst->ops[0], &val)) + if (!tpu_exec_get(tpu, &inst->ops[0], &val)) { + tpu->idle = true; return MODE_READ; + } tpu->acc = MIN(MAX(tpu->acc - val, -999), 999); tpu->pc += 1; return MODE_RUN; @@ -640,7 +642,7 @@ tis_init(struct tis *tis) memset(&tis->out_ports, 0, TIS_MAX_IO_PORTS * sizeof(void *)); tis->steps = 0; tis->show_stats = false; - tis->asm_init = false; + tis->asm_filepath = NULL; } void @@ -659,6 +661,7 @@ tis_deinit(struct tis *tis) free(tis->out_ports[i]); } } + free(tis->asm_filepath); } bool |
