X-Git-Url: http://git.squeep.com/?a=blobdiff_plain;f=dcpu16.c;h=2b39bafd35507092237027462fdf3d1b419502f0;hb=94be117719b907e351bb2bf1096f6195daecd2aa;hp=6ab689888d70a28587f07a47560adf1130d254cd;hpb=57241bb9e6f6b1acb019efe4f32eb758cf9e93d7;p=dcpu16 diff --git a/dcpu16.c b/dcpu16.c index 6ab6898..2b39baf 100644 --- a/dcpu16.c +++ b/dcpu16.c @@ -172,7 +172,7 @@ void dcpu16_cycle_inc(struct dcpu16 *vm, unsigned int n) { /* signal attached hardware */ for (i = 0; i < vm->hw_table_entries_; i++) { TRACE("%s>> notifying %s", __func__, vm->hw_table_[i].name_); - vm->hw_table_[i].cycle(vm, vm->hw_table_[i].data); + vm->hw_table_[i].cycle(vm, &vm->hw_table_[i]); } } } @@ -533,7 +533,7 @@ OP_IMPL(nbi_hwi) { dcpu16_cycle_inc(vm, 4); if (vm->hw_table_[*a].hwi) - vm->hw_table_[*a].hwi(vm, vm->hw_table_[*a].data); + vm->hw_table_[*a].hwi(vm, &vm->hw_table_[*a]); else WARN("hardware 0x%04x has no interrupt handler", *a); } @@ -1369,13 +1369,13 @@ struct dcpu16_hw *dcpu16_hw_new(struct dcpu16 *vm, struct dcpu16_hw_module *mod, } memcpy(hw, mod->template, sizeof *hw); hw->vm = vm; + hw->mod = mod; if (mod->data_init(hw, data)) { vm->warn_cb_("failed to init hw module data"); free(hw); return NULL; } - hw->data_free = mod->data_free; return hw; } @@ -1384,8 +1384,8 @@ struct dcpu16_hw *dcpu16_hw_new(struct dcpu16 *vm, struct dcpu16_hw_module *mod, void dcpu16_hw_del(struct dcpu16_hw **hw) { if (hw) { if (*hw) { - if ((*hw)->data_free) { - (*hw)->data_free(*hw); + if ((*hw)->mod->data_free) { + (*hw)->mod->data_free(*hw); } free(*hw); *hw = NULL; @@ -1393,10 +1393,27 @@ void dcpu16_hw_del(struct dcpu16_hw **hw) { } } -/* dcpu16_hw_add +/* dcpu16_hw_ctl + * invokes per-module controls for hw device + */ +int dcpu16_hw_ctl(struct dcpu16_hw *hw, const char *cmd, void *data_in, void *data_out) { + if (hw) { + if (hw->mod) { + if (hw->mod->ctl) { + if (cmd) { + return hw->mod->ctl(hw, cmd, data_in, data_out); + } + } + } + } + return 0; +} + + +/* dcpu16_hw_attach * registers new 'hardware' device with system */ -int dcpu16_hw_add(struct dcpu16 *vm, struct dcpu16_hw *hw) { +int dcpu16_hw_attach(struct dcpu16 *vm, struct dcpu16_hw *hw) { if (!vm || !hw) return -1; @@ -1485,7 +1502,7 @@ void dcpu16_reset(struct dcpu16 *vm) { /* signal attached hardware */ for (i = 0; i < vm->hw_table_entries_; i++) { if (vm->hw_table_[i].reset) - vm->hw_table_[i].reset(vm, vm->hw_table_[i].data); + vm->hw_table_[i].reset(vm, &vm->hw_table_[i]); } memset(vm->reg, 0, sizeof vm->reg);