+ if ((j % n) != (n - 1))
+ printf("\n");
+}
+
+/* dcpu16_acct_add
+ * Register callback fn to be triggered whenever event matching any events
+ * in bitwise mask occur.
+ */
+int dcpu16_acct_add(struct dcpu16 *vm, dcpu16_acct_event mask, dcpu16_ev_cb_t *fn, void *data) {
+ struct dcpu16_acct_cb cb;
+
+ cb.mask = mask;
+ cb.fn = fn;
+ cb.data = data;
+
+ if (vm->cb_table_entries_ == vm->cb_table_allocated_) {
+ size_t new_entries = vm->cb_table_allocated_ + 32;
+ void *tmp_ptr = realloc(vm->cb_table_, new_entries * sizeof *(vm->cb_table_));
+ if (tmp_ptr == NULL) {
+ fprintf(stderr, "%s():%s", "realloc", strerror(errno));
+ return -1;
+ }
+ vm->cb_table_ = tmp_ptr;
+ vm->cb_table_allocated_ += 32;
+ }
+
+ memcpy(vm->cb_table_ + vm->cb_table_entries_, &cb, sizeof cb);
+ vm->cb_table_entries_++;
+
+ return 0;
+}
+
+/* dcpu16_reset
+ * signals cpu to reset, clearing runstate and ram, then reload any init callbacks
+ */
+void dcpu16_reset(struct dcpu16 *d) {
+ if (!d) return;
+
+ d->cycle = 0;
+ memset(d->reg, 0, sizeof d->reg);
+ d->pc = 0;
+ d->sp = 0;
+ d->o = 0;
+ d->skip_ = 0;
+ memset(d->ram, 0, sizeof d->ram);
+
+ acct_event_(d, DCPU16_ACCT_EV_RESET, 0);