int magicdesk_snapshot_read_module(snapshot_t *s) { uint8_t vmajor, vminor; snapshot_module_t *m; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if ((vmajor != CART_DUMP_VER_MAJOR) || (vminor != CART_DUMP_VER_MINOR)) { snapshot_module_close(m); return -1; } if (0 || (SMR_B(m, ®val) < 0) || (SMR_B(m, &bankmask) < 0) || (SMR_BA(m, roml_banks, 0x2000 * MAXBANKS) < 0)) { snapshot_module_close(m); return -1; } snapshot_module_close(m); if (magicdesk_common_attach() == -1) { return -1; } magicdesk_io1_store(0xde00, regval); return 0; }
static int userport_rtc_read_snapshot_module(snapshot_t *s) { BYTE major_version, minor_version; snapshot_module_t *m; /* enable device */ set_userport_rtc_enabled(1, NULL); m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) { return -1; } /* Do not accept versions higher than current */ if (major_version > SNAP_MAJOR || minor_version > SNAP_MINOR) { snapshot_set_error(SNAPSHOT_MODULE_HIGHER_VERSION); goto fail; } if (0 || SMR_B(m, &ds1307_pb0_sda) < 0 || SMR_B(m, &ds1307_pb1_scl) < 0) { goto fail; } snapshot_module_close(m); return ds1307_read_snapshot(ds1307_context, s); fail: snapshot_module_close(m); return -1; }
static int userport_digimax_read_snapshot_module(snapshot_t *s) { BYTE major_version, minor_version; snapshot_module_t *m; /* enable device */ set_digimax_enabled(1, NULL); m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) { return -1; } /* Do not accept versions higher than current */ if (major_version > SNAP_MAJOR || minor_version > SNAP_MINOR) { snapshot_set_error(SNAPSHOT_MODULE_HIGHER_VERSION); goto fail; } if (0 || (SMR_B(m, &userport_digimax_address) < 0) || (SMR_BA(m, digimax_sound_data, 4) < 0) || (SMR_B(m, &snd.voice0) < 0) || (SMR_B(m, &snd.voice1) < 0) || (SMR_B(m, &snd.voice2) < 0) || (SMR_B(m, &snd.voice3) < 0)) { goto fail; } return snapshot_module_close(m); fail: snapshot_module_close(m); return -1; }
int finalexpansion_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; BYTE *cart_flash = NULL; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if (vmajor != VIC20CART_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } if (!cart_ram) { cart_ram = lib_malloc(CART_RAM_SIZE); } if (!cart_flash) { cart_flash = lib_malloc(CART_ROM_SIZE); } flash040core_init(&flash_state, maincpu_alarm_context, FLASH040_TYPE_B, cart_flash); if (0 || (SMR_B(m, ®ister_a) < 0) || (SMR_B(m, ®ister_b) < 0) || (SMR_B(m, &lock_bit) < 0) || (SMR_BA(m, cart_ram, CART_RAM_SIZE) < 0) || (SMR_BA(m, flash_state.flash_data, CART_ROM_SIZE) < 0)) { snapshot_module_close(m); flash040core_shutdown(&flash_state); lib_free(cart_ram); lib_free(cart_flash); cart_ram = NULL; cart_flash = NULL; return -1; } snapshot_module_close(m); if ((flash040core_snapshot_read_module(s, &flash_state, FLASH_SNAP_MODULE_NAME) < 0)) { flash040core_shutdown(&flash_state); lib_free(cart_ram); lib_free(cart_flash); cart_ram = NULL; cart_flash = NULL; return -1; } mem_cart_blocks = VIC_CART_RAM123 | VIC_CART_BLK1 | VIC_CART_BLK2 | VIC_CART_BLK3 | VIC_CART_BLK5 | VIC_CART_IO2 | VIC_CART_IO3; mem_initialize_memory(); return 0; }
int megacart_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if (vmajor != VIC20CART_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } if (!cart_ram) { cart_ram = lib_malloc(CART_RAM_SIZE); } if (!cart_nvram) { cart_nvram = lib_malloc(CART_NVRAM_SIZE); } if (!cart_rom) { cart_rom = lib_malloc(CART_ROM_SIZE); } if (0 || (SMR_B(m, &bank_low_reg) < 0) || (SMR_B(m, &bank_high_reg) < 0) || (SMR_B_INT(m, &oe_flop) < 0) || (SMR_B_INT(m, &nvram_en_flop) < 0) || (SMR_BA(m, cart_ram, CART_RAM_SIZE) < 0) || (SMR_BA(m, cart_rom, CART_ROM_SIZE) < 0) || (SMR_BA(m, cart_nvram, CART_NVRAM_SIZE) < 0)) { snapshot_module_close(m); lib_free(cart_ram); lib_free(cart_nvram); lib_free(cart_rom); cart_ram = NULL; cart_nvram = NULL; cart_rom = NULL; return -1; } snapshot_module_close(m); cart_rom_low = cart_rom; cart_rom_high = cart_rom + 0x100000; reset_mode = BUTTON_RESET; mem_cart_blocks = VIC_CART_RAM123 | VIC_CART_BLK1 | VIC_CART_BLK2 | VIC_CART_BLK3 | VIC_CART_BLK5 | VIC_CART_IO2 | VIC_CART_IO3; mem_initialize_memory(); return 0; }
int vic_fp_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if (vmajor != VIC20CART_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } if (!cart_ram) { cart_ram = lib_malloc(CART_RAM_SIZE); } if (!cart_rom) { cart_rom = lib_malloc(CART_ROM_SIZE); } flash040core_init(&flash_state, maincpu_alarm_context, FLASH040_TYPE_032B_A0_1_SWAP, cart_rom); if (0 || (SMR_B(m, &cart_bank_reg) < 0) || (SMR_B(m, &cart_cfg_reg) < 0) || (SMR_BA(m, cart_ram, CART_RAM_SIZE) < 0) || (SMR_BA(m, cart_rom, CART_ROM_SIZE) < 0)) { snapshot_module_close(m); lib_free(cart_ram); lib_free(cart_rom); cart_ram = NULL; cart_rom = NULL; return -1; } snapshot_module_close(m); if ((flash040core_snapshot_read_module(s, &flash_state, FLASH_SNAP_MODULE_NAME) < 0)) { flash040core_shutdown(&flash_state); lib_free(cart_ram); lib_free(cart_rom); cart_ram = NULL; cart_rom = NULL; return -1; } CART_CFG_INIT(cart_cfg_reg); mem_cart_blocks = VIC_CART_RAM123 | VIC_CART_BLK1 | VIC_CART_BLK2 | VIC_CART_BLK3 | VIC_CART_BLK5 | VIC_CART_IO2; mem_initialize_memory(); return 0; }
int easyflash_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if ((vmajor != CART_DUMP_VER_MAJOR) || (vminor != CART_DUMP_VER_MINOR)) { snapshot_module_close(m); return -1; } if (0 || (SMR_B_INT(m, &easyflash_jumper) < 0) || (SMR_B(m, &easyflash_register_00) < 0) || (SMR_B(m, &easyflash_register_02) < 0) || (SMR_BA(m, easyflash_ram, 256) < 0) || (SMR_BA(m, roml_banks, 0x80000) < 0) || (SMR_BA(m, romh_banks, 0x80000) < 0)) { snapshot_module_close(m); return -1; } snapshot_module_close(m); easyflash_state_low = lib_malloc(sizeof(flash040_context_t)); easyflash_state_high = lib_malloc(sizeof(flash040_context_t)); flash040core_init(easyflash_state_low, maincpu_alarm_context, FLASH040_TYPE_B, roml_banks); flash040core_init(easyflash_state_high, maincpu_alarm_context, FLASH040_TYPE_B, romh_banks); if (0 || (flash040core_snapshot_read_module(s, easyflash_state_low, FLASH_SNAP_MODULE_NAME) < 0) || (flash040core_snapshot_read_module(s, easyflash_state_low, FLASH_SNAP_MODULE_NAME) < 0)) { flash040core_shutdown(easyflash_state_low); flash040core_shutdown(easyflash_state_high); lib_free(easyflash_state_low); lib_free(easyflash_state_high); return -1; } easyflash_common_attach("dummy"); /* remove dummy filename, set filetype to none */ lib_free(easyflash_filename); easyflash_filename = NULL; easyflash_filetype = 0; return 0; }
static int mem_read_ram_snapshot_module(snapshot_t *p) { BYTE vmajor, vminor; snapshot_module_t *m; BYTE config; m = snapshot_module_open(p, SNAP_MEM_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if (vmajor != VIC20MEM_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } SMR_B(m, &config); SMR_B(m, &vic20_cpu_last_data); SMR_B(m, &vic20_v_bus_last_data); SMR_B(m, &vic20_v_bus_last_high); SMR_BA(m, mem_ram, 0x0400); SMR_BA(m, mem_ram + 0x1000, 0x1000); resources_set_int("RAMBlock0", (config & 1) ? 1 : 0 ); if (config & 1) { SMR_BA(m, mem_ram + 0x0400, 0x0c00); } resources_set_int("RAMBlock1", (config & 2) ? 1 : 0 ); if (config & 2) { SMR_BA(m, mem_ram + 0x2000, 0x2000); } resources_set_int("RAMBlock2", (config & 4) ? 1 : 0 ); if (config & 4) { SMR_BA(m, mem_ram + 0x4000, 0x2000); } resources_set_int("RAMBlock3", (config & 8) ? 1 : 0 ); if (config & 8) { SMR_BA(m, mem_ram + 0x6000, 0x2000); } resources_set_int("RAMBlock5", (config & 32) ? 1 : 0 ); if (config & 32) { SMR_BA(m, mem_ram + 0xA000, 0x2000); } snapshot_module_close(m); mem_initialize_memory(); return 0; }
int maincpu_snapshot_read_module(snapshot_t *s) { BYTE a, x, y, sp, status; WORD pc; BYTE major, minor; snapshot_module_t *m; m = snapshot_module_open(s, snap_module_name, &major, &minor); if (m == NULL) { return -1; } /* FIXME: This is a mighty kludge to prevent VIC-II from stealing the wrong number of cycles. */ maincpu_rmw_flag = 0; /* XXX: Assumes `CLOCK' is the same size as a `DWORD'. */ if (0 || SMR_DW(m, &maincpu_clk) < 0 || SMR_B(m, &a) < 0 || SMR_B(m, &x) < 0 || SMR_B(m, &y) < 0 || SMR_B(m, &sp) < 0 || SMR_W(m, &pc) < 0 || SMR_B(m, &status) < 0 || SMR_DW_UINT(m, &last_opcode_info) < 0) { goto fail; } MOS6510_REGS_SET_A(&maincpu_regs, a); MOS6510_REGS_SET_X(&maincpu_regs, x); MOS6510_REGS_SET_Y(&maincpu_regs, y); MOS6510_REGS_SET_SP(&maincpu_regs, sp); MOS6510_REGS_SET_PC(&maincpu_regs, pc); MOS6510_REGS_SET_STATUS(&maincpu_regs, status); if (interrupt_read_snapshot(maincpu_int_status, m) < 0) { goto fail; } if (interrupt_read_new_snapshot(maincpu_int_status, m) < 0) { goto fail; } return snapshot_module_close(m); fail: if (m != NULL) { snapshot_module_close(m); } return -1; }
static int paperclip64_read_snapshot(struct snapshot_s *s, int port) { BYTE major_version, minor_version; snapshot_module_t *m; m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) { return -1; } /* Do not accept versions higher than current */ if (major_version > SNAP_MAJOR || minor_version > SNAP_MINOR) { snapshot_set_error(SNAPSHOT_MODULE_HIGHER_VERSION); goto fail; } if (0 || SMR_DW_INT(m, &counter) < 0 || SMR_B(m, &command) < 0 || SMR_B_INT(m, &state) < 0) { goto fail; } return snapshot_module_close(m); fail: snapshot_module_close(m); return -1; }
int sfx_soundsampler_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if ((vmajor != CART_DUMP_VER_MAJOR) || (vminor != CART_DUMP_VER_MINOR)) { snapshot_module_close(m); return -1; } if (0 || (SMR_B(m, &sfx_soundsampler_sound_data) < 0)) { snapshot_module_close(m); return -1; } if (!sfx_soundsampler_sound_chip.chip_enabled) { set_sfx_soundsampler_enabled(1, NULL); } sound_store(sfx_soundsampler_sound_chip_offset, sfx_soundsampler_sound_data, 0); snapshot_module_close(m); return 0; }
int snapshot64_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if ((vmajor != CART_DUMP_VER_MAJOR) || (vminor != CART_DUMP_VER_MINOR)) { snapshot_module_close(m); return -1; } if (0 || (SMR_B(m, &romconfig) < 0) || (SMR_BA(m, roml_banks, 0x1000) < 0)) { snapshot_module_close(m); return -1; } snapshot_module_close(m); return snapshot64_common_attach(); }
int c128_snapshot_read_module(snapshot_t *s) { BYTE major_version, minor_version; snapshot_module_t *m; WORD i; BYTE byte; /* Main memory module. */ m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) return -1; if (major_version > SNAP_MAJOR || minor_version > SNAP_MINOR) { log_error(c128_snapshot_log, "MEM: Snapshot module version (%d.%d) newer than %d.%d.", major_version, minor_version, SNAP_MAJOR, SNAP_MINOR); goto fail; } for (i = 0; i < 11; i++) { if (SMR_B(m, &byte) < 0) goto fail; mmu_store(i, byte); /* Assuming no side-effects */ } if (0 || SMR_BA(m, mem_ram, C128_RAM_SIZE) < 0) goto fail; /* pla_config_changed(); */ if (snapshot_module_close(m) < 0) goto fail; m = NULL; if (mem_read_rom_snapshot_module(s) < 0) goto fail; if (cartridge_snapshot_read_modules(s) < 0) { goto fail; } ui_update_menus(); return 0; fail: if (m != NULL) snapshot_module_close(m); return -1; }
int fdc_snapshot_read_module(snapshot_t *p, int fnum) { BYTE vmajor, vminor; BYTE byte, ndrv; DWORD dword; snapshot_module_t *m; char *name; name = lib_msprintf("FDC%d", fnum); m = snapshot_module_open(p, name, &vmajor, &vminor); lib_free(name); if (m == NULL) { log_message(fdc_log, "Could not find snapshot module %s", name); return -1; } if (vmajor != FDC_DUMP_VER_MAJOR) { log_error(fdc_log, "Snapshot module version (%d.%d) newer than %d.%d.", vmajor, vminor, FDC_DUMP_VER_MAJOR, FDC_DUMP_VER_MINOR); snapshot_module_close(m); return -1; } SMR_B(m, &byte); if (byte > FDC_LAST_STATE) { snapshot_module_close(m); return -1; } fdc[fnum].fdc_state = byte; /* clk till next invocation */ SMR_DW(m, &dword); fdc[fnum].alarm_clk = drive_clk[fnum] + dword; alarm_set(fdc[fnum].fdc_alarm, fdc[fnum].alarm_clk); /* number of drives - so far 1 only */ SMR_B(m, &ndrv); /* last accessed track/sector */ SMR_B(m, &byte); fdc[fnum].last_track = byte; SMR_B(m, &byte); fdc[fnum].last_sector = byte; if (ndrv > 1) { /* ignore drv 0 values */ SMR_B(m, &byte); SMR_B(m, &byte); } if (snapshot_module_close(m) < 0) return -1; return 0; }
int behrbonz_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if (vmajor != VIC20CART_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } if (!cart_rom) { cart_rom = lib_malloc(CART_ROM_SIZE); } if (0 || (SMR_B(m, &bank_reg) < 0) || (SMR_B(m, &reset_mode) < 0) || (SMR_B(m, &write_once) < 0) || (SMR_BA(m, cart_rom, CART_ROM_SIZE) < 0)) { snapshot_module_close(m); lib_free(cart_rom); cart_rom = NULL; return -1; } snapshot_module_close(m); mem_cart_blocks = VIC_CART_BLK1 | VIC_CART_BLK2 | VIC_CART_BLK3 | VIC_CART_BLK5 | VIC_CART_IO3; mem_initialize_memory(); return 0; }
static int mem_read_rom_snapshot_module(snapshot_t *p) { BYTE vmajor, vminor; snapshot_module_t *m; BYTE config; int trapfl; m = snapshot_module_open(p, SNAP_ROM_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return 0; /* optional */ } if (vmajor != VIC20ROM_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } /* disable traps before loading the ROM */ resources_get_int("VirtualDevices", &trapfl); resources_set_int("VirtualDevices", 0); /* old cart system ROMs (ignored) */ SMR_B(m, &config); /* read kernal */ SMR_BA(m, vic20memrom_kernal_rom, 0x2000); /* read basic */ SMR_BA(m, vic20memrom_basic_rom, 0x2000); SMR_BA(m, vic20memrom_chargen_rom, 0x1000); vic20rom_kernal_checksum(); vic20rom_basic_checksum(); log_warning(vic20_snapshot_log, "Dumped Romset files and saved settings will " "represent\nthe state before loading the snapshot!"); /* enable traps again when necessary */ resources_set_int("VirtualDevices", trapfl); snapshot_module_close(m); mem_initialize_memory(); return 0; }
int mypia_snapshot_read_module(snapshot_t * p) { BYTE vmajor, vminor; BYTE byte; snapshot_module_t *m; my_restore_int(pia_int_num, 0); /* just in case */ m = snapshot_module_open(p, snap_module_name, &vmajor, &vminor); if (m == NULL) return -1; if (vmajor != PIA_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } SMR_B(m, &mypia.port_a); SMR_B(m, &mypia.ddr_a); SMR_B(m, &mypia.ctrl_a); SMR_B(m, &mypia.port_b); SMR_B(m, &mypia.ddr_b); SMR_B(m, &mypia.ctrl_b); SMR_B(m, &byte); mypia.ca_state = (byte & 0x80) ? 1 : 0; mypia.cb_state = (byte & 0x80) ? 1 : 0; pia_set_ca2(mypia.ca_state); pia_set_cb2(mypia.cb_state); byte = mypia.port_a | ~mypia.ddr_a; undump_pa(byte); byte = mypia.port_b | ~mypia.ddr_b; undump_pb(byte); if (0 || ((mypia.ctrl_a & 0x81) == 0x81) || ((mypia.ctrl_a & 0x68) == 0x48) || ((mypia.ctrl_b & 0x81) == 0x81) || ((mypia.ctrl_b & 0x68) == 0x48) ) { my_restore_int(pia_int_num, 1); } return snapshot_module_close(m); }
int digimax_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; int temp_digimax_address; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if ((vmajor != CART_DUMP_VER_MAJOR) || (vminor != CART_DUMP_VER_MINOR)) { snapshot_module_close(m); return -1; } if (0 || (SMR_DW_INT(m, &temp_digimax_address) < 0) /* FIXME: Implement the userport part in userport_digimax.c */ #if 0 || (SMR_B(m, &digimax_userport_address) < 0) || (SMR_B(m, &digimax_userport_direction_A) < 0) || (SMR_B(m, &digimax_userport_direction_B) < 0) #endif || (SMR_BA(m, digimax_sound_data, 4) < 0) || (SMR_B(m, &snd.voice0) < 0) || (SMR_B(m, &snd.voice1) < 0) || (SMR_B(m, &snd.voice2) < 0) || (SMR_B(m, &snd.voice3) < 0)) { snapshot_module_close(m); return -1; } snapshot_module_close(m); /* HACK set address to an invalid value, then use the function */ digimax_address = -1; set_digimax_base(temp_digimax_address, NULL); return digimax_enable(); }
int mc6821core_snapshot_read_data(mc6821_state *ctx, snapshot_module_t *m) { if (m == NULL) { return -1; } if (0 || (SMR_B(m, &ctx->ctrlA) < 0) || (SMR_B(m, &ctx->ctrlB) < 0) || (SMR_B(m, &ctx->dataA) < 0) || (SMR_B(m, &ctx->dataB) < 0) || (SMR_B(m, &ctx->ddrA) < 0) || (SMR_B(m, &ctx->ddrB) < 0) || (SMR_B_INT(m, &ctx->CA2) < 0) || (SMR_B_INT(m, &ctx->CA2state) < 0) || (SMR_B_INT(m, &ctx->CB2) < 0) || (SMR_B_INT(m, &ctx->CB2state) < 0)) { snapshot_module_close(m); return -1; } return 0; }
int vic20cart_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; int new_cart_type, cartridge_reset; BYTE i; BYTE number_of_carts; int cart_ids[VIC20CART_DUMP_MAX_CARTS]; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if (vmajor != VIC20CART_DUMP_VER_MAJOR) { goto fail; } if (SMR_DW_INT(m, &new_cart_type) < 0) { goto fail; } if (SMR_B(m, &number_of_carts) < 0) { goto fail; } /* Not much to do if no carts in snapshot */ if (number_of_carts == 0) { return snapshot_module_close(m); } if (number_of_carts > VIC20CART_DUMP_MAX_CARTS) { DBG(("CART snapshot read: carts %i > max %i\n", number_of_carts, VIC20CART_DUMP_MAX_CARTS)); goto fail; } /* Read cart IDs */ for (i = 0; i < number_of_carts; i++) { if (SMR_DW_INT(m, &cart_ids[i]) < 0) { goto fail; } } snapshot_module_close(m); /* disable cartridge reset while detaching old cart */ resources_get_int("CartridgeReset", &cartridge_reset); resources_set_int("CartridgeReset", 0); cartridge_detach_image(-1); resources_set_int("CartridgeReset", cartridge_reset); /* disallow "set as default" and write back */ cartridge_is_from_snapshot = 1; vic20cart_type = new_cart_type; mem_cartridge_type = new_cart_type; /* Read individual cart data */ for (i = 0; i < number_of_carts; i++) { switch (cart_ids[i]) { case CARTRIDGE_VIC20_FINAL_EXPANSION: if (finalexpansion_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_VIC20_IO2_RAM: if (ioramcart_io2_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_VIC20_IO3_RAM: if (ioramcart_io3_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_VIC20_MEGACART: if (megacart_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_VIC20_UM: if (vic_um_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_VIC20_IEEE488: if (vic20_ieee488_snapshot_read_module(s) < 0) { return -1; } break; #ifdef HAVE_MIDI case CARTRIDGE_MIDI_MAPLIN: if (vic20_midi_snapshot_read_module(s) < 0) { return -1; } break; #endif case CARTRIDGE_VIC20_SIDCART: if (sidcart_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_VIC20_FP: if (vic_fp_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_ACIA: if (aciacart_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_DIGIMAX: if (digimax_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_DS12C887RTC: if (ds12c887rtc_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_GEORAM: if (georam_read_snapshot_module(s) < 0) { return -1; } break; case CARTRIDGE_SFX_SOUND_EXPANDER: if (sfx_soundexpander_snapshot_read_module(s) < 0) { return -1; } break; case CARTRIDGE_SFX_SOUND_SAMPLER: if (sfx_soundsampler_snapshot_read_module(s) < 0) { return -1; } break; #ifdef HAVE_TFE case CARTRIDGE_TFE: if (tfe_snapshot_read_module(s) < 0) { return -1; } break; #endif } } if (vic20cart_type == CARTRIDGE_VIC20_GENERIC) { if (generic_snapshot_read_module(s) < 0) { return -1; } } return 0; fail: snapshot_module_close(m); return -1; }
static int mem_read_rom_snapshot_module(snapshot_t *p) { BYTE vmajor, vminor; snapshot_module_t *m; BYTE config; int i, trapfl; m = snapshot_module_open(p, module_rom_name, &vmajor, &vminor); if (m == NULL) return 0; /* optional */ if (vmajor != CBM2ROM_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } /* disable traps before loading the ROM */ resources_get_int("VirtualDevices", &trapfl); resources_set_int("VirtualDevices", 0); SMR_B(m, &config); /* kernal */ SMR_BA(m, mem_rom + 0xe000, 0x2000); /* basic */ SMR_BA(m, mem_rom + 0x8000, 0x4000); /* chargen */ if (config & 32) { SMR_BA(m, mem_chargen_rom, 0x1000); } else { SMR_BA(m, mem_chargen_rom, 0x0800); SMR_BA(m, mem_chargen_rom + 0x1000, 0x0800); /* Inverted chargen into second half. This is a hardware feature. */ for (i = 0; i < 2048; i++) { mem_chargen_rom[i + 2048] = mem_chargen_rom[i] ^ 0xff; mem_chargen_rom[i + 6144] = mem_chargen_rom[i + 4096] ^ 0xff; } } if (config & 2) { SMR_BA(m, mem_rom + 0x1000, 0x1000); } if (config & 4) { SMR_BA(m, mem_rom + 0x2000, 0x2000); } if (config & 8) { SMR_BA(m, mem_rom + 0x4000, 0x2000); } if (config & 16) { SMR_BA(m, mem_rom + 0x6000, 0x2000); } log_warning(cbm2_snapshot_log, "Dumped Romset files and saved settings will " "represent\nthe state before loading the snapshot!"); cbm2rom_checksum(); /* enable traps again when necessary */ resources_set_int("VirtualDevices", trapfl); snapshot_module_close(m); return 0; }
static int mem_read_ram_snapshot_module(snapshot_t *p) { BYTE byte, vmajor, vminor; snapshot_module_t *m; BYTE config, hwconfig; int memsize; int effective_ramsize, effective_start; int bank0; m = snapshot_module_open(p, module_name, &vmajor, &vminor); if (m == NULL) return -1; if (vmajor != CBM2MEM_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } SMR_B(m, &byte); memsize = ((int)byte) & 0xff; SMR_B(m, &config); SMR_B(m, &hwconfig); resources_set_int("ModelLine", hwconfig & 3); SMR_B(m, &byte); cbm2mem_set_bank_exec(byte); SMR_B(m, &byte); cbm2mem_set_bank_ind(byte); SMR_BA(m, mem_ram + 0xf0000, 0x0800); SMR_BA(m, mem_rom + 0xd000, 0x0800); /* calculate start and size of RAM to load */ /* ramsize starts counting at 0x10000 if less than 512k */ bank0 = config & 64; effective_ramsize = memsize << 7; effective_start = 0x10000; if (bank0 || effective_ramsize >= 512) { effective_start = 0; } if (bank0 && effective_ramsize < 512) { effective_ramsize -= 64; } SMR_BA(m, mem_ram + effective_start, memsize << 17); ramsize = effective_ramsize; cart08_ram = config & 1; cart1_ram = config & 2; cart2_ram = config & 4; cart4_ram = config & 8; cart6_ram = config & 16; cartC_ram = config & 32; if (memsize < 4) { SMR_BA(m, mem_ram + 0x10000, memsize << 17); } else { SMR_BA(m, mem_ram, memsize << 17); } if (memsize < 4) { /* if 1M memory, bank 15 is included */ if (config & 1) { SMR_BA(m, mem_ram + 0xf0800, 0x0800); } if (config & 2) { SMR_BA(m, mem_ram + 0xf1000, 0x1000); } if (config & 4) { SMR_BA(m, mem_ram + 0xf2000, 0x2000); } if (config & 8) { SMR_BA(m, mem_ram + 0xf4000, 0x2000); } if (config & 16) { SMR_BA(m, mem_ram + 0xf6000, 0x2000); } if (config & 32) { SMR_BA(m, mem_ram + 0xfc000, 0x1000); } } mem_initialize_memory(); snapshot_module_close(m); return 0; }
int tape_snapshot_read_module(snapshot_t *s) { BYTE major_version, minor_version; snapshot_module_t *m; unsigned int snap_type; char snap_module_name[] = "TAPE"; tap_t *tap; t64_t *t64; if (tape_snapshot_read_tapimage_module(s) < 0 || tape_snapshot_read_t64image_module(s) < 0) return -1; m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) { /* no tape attached */ tape_image_detach_internal(1); return 0; } if (0 || SMR_B_INT(m, (int *)&tape_image_dev1->read_only) < 0 || SMR_B_INT(m, (int *)&snap_type) < 0) { snapshot_module_close(m); return -1; } if (snap_type != tape_image_dev1->type) { /* attached image type is not correct */ log_error(tape_snapshot_log, "No tape image attached or type not correct."); snapshot_module_close(m); return -1; } switch (tape_image_dev1->type) { case TAPE_TYPE_T64: t64 = (t64_t*)tape_image_dev1->data; break; case TAPE_TYPE_TAP: tap = (tap_t*)tape_image_dev1->data; if (tap == NULL || SMR_DW(m, (DWORD*)&tap->size) < 0 || SMR_B(m, &tap->version) < 0 || SMR_B(m, &tap->system) < 0 || SMR_DW(m, (DWORD*)&tap->current_file_seek_position) < 0 || SMR_DW(m, (DWORD*)&tap->offset) < 0 || SMR_DW(m, (DWORD*)&tap->cycle_counter) < 0 || SMR_DW(m, (DWORD*)&tap->cycle_counter_total) < 0 || SMR_DW(m, (DWORD*)&tap->counter) < 0 || SMR_DW(m, (DWORD*)&tap->mode) < 0 || SMR_DW(m, (DWORD*)&tap->read_only) < 0 || SMR_DW(m, (DWORD*)&tap->has_changed) < 0) { snapshot_module_close(m); return -1; } break; default: break; } snapshot_module_close(m); if (datasette_read_snapshot(s) < 0) return -1; return 0; }
/*! \brief Read the snapshot module for the ACIA \param p Pointer to the snapshot data \return 0 on success, -1 on error \remark The format has been extended in VICE 2.0.9. However, the version number remained the same. This function tries to read the new values. If they are not available, it mimics the old behaviour and reports success, anyway. \remark It is unclear if it is sensible to mimic the old behaviour, as the old implementation was severely broken. */ int myacia_snapshot_read_module(snapshot_t *p) { BYTE vmajor, vminor; BYTE byte; DWORD dword; snapshot_module_t *m; alarm_unset(acia.alarm_tx); /* just in case we don't find module */ alarm_unset(acia.alarm_rx); /* just in case we don't find module */ acia.alarm_active_tx = 0; acia.alarm_active_rx = 0; mycpu_set_int_noclk(acia.int_num, 0); m = snapshot_module_open(p, module_name, &vmajor, &vminor); if (m == NULL) { return -1; } if (vmajor != ACIA_DUMP_VER_MAJOR) { snapshot_module_close(m); return -1; } SMR_B(m, &acia.txdata); SMR_B(m, &acia.rxdata); acia.irq = 0; SMR_B(m, &acia.status); if (acia.status & ACIA_SR_BITS_IRQ) { acia.status &= ~ACIA_SR_BITS_IRQ; acia.irq = 1; mycpu_set_int_noclk(acia.int_num, acia.irq_type); } else { mycpu_set_int_noclk(acia.int_num, 0); } SMR_B(m, &acia.cmd); if ((acia.cmd & ACIA_CMD_BITS_DTR_ENABLE_RECV_AND_IRQ) && (acia.fd < 0)) { acia.fd = rs232drv_open(acia.device); acia_set_handshake_lines(); } else { if ((acia.fd >= 0) && !(acia.cmd & ACIA_CMD_BITS_DTR_ENABLE_RECV_AND_IRQ)) { rs232drv_close(acia.fd); acia.fd = -1; } } SMR_B(m, &acia.ctrl); set_acia_ticks(); SMR_B(m, &byte); acia.in_tx = byte; SMR_DW(m, &dword); if (dword) { acia.alarm_clk_tx = myclk + dword; alarm_set(acia.alarm_tx, acia.alarm_clk_tx); acia.alarm_active_tx = 1; /* * for compatibility reasons of old snapshots with new ones, * set the RX alarm to the same value. * if we have a new snapshot (2.0.9 and up), this will be * overwritten directly afterwards. */ acia.alarm_clk_rx = myclk + dword; alarm_set(acia.alarm_rx, acia.alarm_clk_rx); acia.alarm_active_rx = 1; } /* * this is new with VICE 2.0.9; thus, only use the settings * if it does exist. */ if (SMR_DW(m, &dword) >= 0) { if (dword) { acia.alarm_clk_rx = myclk + dword; alarm_set(acia.alarm_rx, acia.alarm_clk_rx); acia.alarm_active_rx = 1; } else { alarm_unset(acia.alarm_rx); acia.alarm_active_rx = 0; } } if (snapshot_module_close(m) < 0) { return -1; } return 0; }
int drivecpu_snapshot_read_module(drive_context_t *drv, snapshot_t *s) { BYTE major, minor; snapshot_module_t *m; BYTE a, x, y, sp, status; WORD pc; drivecpu_context_t *cpu; cpu = drv->cpu; m = snapshot_module_open(s, drv->cpu->snap_module_name, &major, &minor); if (m == NULL) { return -1; } /* Before we start make sure all devices are reset. */ drivecpu_reset(drv); /* XXX: Assumes `CLOCK' is the same size as a `DWORD'. */ if (0 || SMR_DW(m, drv->clk_ptr) < 0 || SMR_B(m, &a) < 0 || SMR_B(m, &x) < 0 || SMR_B(m, &y) < 0 || SMR_B(m, &sp) < 0 || SMR_W(m, &pc) < 0 || SMR_B(m, &status) < 0 || SMR_DW_UINT(m, &(cpu->last_opcode_info)) < 0 || SMR_DW(m, &(cpu->last_clk)) < 0 || SMR_DW(m, &(cpu->cycle_accum)) < 0 || SMR_DW(m, &(cpu->last_exc_cycles)) < 0 || SMR_DW(m, &(cpu->stop_clk)) < 0 ) { goto fail; } MOS6510_REGS_SET_A(&(cpu->cpu_regs), a); MOS6510_REGS_SET_X(&(cpu->cpu_regs), x); MOS6510_REGS_SET_Y(&(cpu->cpu_regs), y); MOS6510_REGS_SET_SP(&(cpu->cpu_regs), sp); MOS6510_REGS_SET_PC(&(cpu->cpu_regs), pc); MOS6510_REGS_SET_STATUS(&(cpu->cpu_regs), status); log_message(drv->drive->log, "RESET (For undump)."); interrupt_cpu_status_reset(cpu->int_status); machine_drive_reset(drv); if (interrupt_read_snapshot(cpu->int_status, m) < 0) { goto fail; } if (drv->drive->type == DRIVE_TYPE_1540 || drv->drive->type == DRIVE_TYPE_1541 || drv->drive->type == DRIVE_TYPE_1541II || drv->drive->type == DRIVE_TYPE_1551 || drv->drive->type == DRIVE_TYPE_1570 || drv->drive->type == DRIVE_TYPE_1571 || drv->drive->type == DRIVE_TYPE_1571CR || drv->drive->type == DRIVE_TYPE_2031) { if (SMR_BA(m, drv->drive->drive_ram, 0x800) < 0) { goto fail; } } if (drv->drive->type == DRIVE_TYPE_1581 || drv->drive->type == DRIVE_TYPE_2000 || drv->drive->type == DRIVE_TYPE_4000) { if (SMR_BA(m, drv->drive->drive_ram, 0x2000) < 0) { goto fail; } } if (drive_check_old(drv->drive->type)) { if (SMR_BA(m, drv->drive->drive_ram, 0x1100) < 0) { goto fail; } } /* Update `*bank_base'. */ JUMP(reg_pc); if (interrupt_read_new_snapshot(drv->cpu->int_status, m) < 0) { goto fail; } return snapshot_module_close(m); fail: if (m != NULL) { snapshot_module_close(m); } return -1; }
int sfx_soundexpander_snapshot_read_module(snapshot_t *s) { BYTE vmajor, vminor; snapshot_module_t *m; int temp_chip; FM_OPL *chip = NULL; int temp_connect1; int x, y; m = snapshot_module_open(s, SNAP_MODULE_NAME, &vmajor, &vminor); if (m == NULL) { return -1; } if ((vmajor != CART_DUMP_VER_MAJOR) || (vminor != CART_DUMP_VER_MINOR)) { snapshot_module_close(m); return -1; } if (0 || (SMR_DW_INT(m, &temp_chip) < 0)) { snapshot_module_close(m); return -1; } if (sfx_soundexpander_sound_chip.chip_enabled) { set_sfx_soundexpander_enabled(0, NULL); } set_sfx_soundexpander_chip(temp_chip, NULL); set_sfx_soundexpander_enabled(1, NULL); chip = (temp_chip == 3526) ? YM3526_chip : YM3812_chip; if (0 || (SMR_B(m, &snd.command) < 0)) { snapshot_module_close(m); return -1; } for (x = 0; x < 9; x++) { for (y = 0; y < 2; y++) { if (0 || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].ar) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].dr) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].rr) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].KSR) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].ksl) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].ksr) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].mul) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].Cnt) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].Incr) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].FB) < 0) || (SMR_DW_INT(m, &temp_connect1) < 0) || (SMR_DW_INT(m, &chip->P_CH[x].SLOT[y].op1_out[0]) < 0) || (SMR_DW_INT(m, &chip->P_CH[x].SLOT[y].op1_out[1]) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].CON) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].eg_type) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].state) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].TL) < 0) || (SMR_DW_INT(m, &chip->P_CH[x].SLOT[y].TLL) < 0) || (SMR_DW_INT(m, &chip->P_CH[x].SLOT[y].volume) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].sl) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].eg_sh_ar) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].eg_sel_ar) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].eg_sh_dr) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].eg_sel_dr) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].eg_sh_rr) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].eg_sel_rr) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].key) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].SLOT[y].AMmask) < 0) || (SMR_B(m, &chip->P_CH[x].SLOT[y].vib) < 0) || (SMR_W(m, &chip->P_CH[x].SLOT[y].wavetable) < 0)) { snapshot_module_close(m); return -1; } set_connect1(chip->P_CH[x].SLOT[y].connect1, temp_connect1); } if (0 || (SMR_DW_UINT(m, &chip->P_CH[x].block_fnum) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].fc) < 0) || (SMR_DW_UINT(m, &chip->P_CH[x].ksl_base) < 0) || (SMR_B(m, &chip->P_CH[x].kcode) < 0)) { snapshot_module_close(m); return -1; } } if (0 || (SMR_DW_UINT(m, &chip->eg_cnt) < 0) || (SMR_DW_UINT(m, &chip->eg_timer) < 0) || (SMR_DW_UINT(m, &chip->eg_timer_add) < 0) || (SMR_DW_UINT(m, &chip->eg_timer_overflow) < 0) || (SMR_B(m, &chip->rhythm) < 0)) { snapshot_module_close(m); return -1; } for (x = 0; x < 1024; x++) { if (0 || (SMR_DW_UINT(m, &chip->fn_tab[x]) < 0)) { snapshot_module_close(m); return -1; } } if (0 || (SMR_B(m, &chip->lfo_am_depth) < 0) || (SMR_B(m, &chip->lfo_pm_depth_range) < 0) || (SMR_DW_UINT(m, &chip->lfo_am_cnt) < 0) || (SMR_DW_UINT(m, &chip->lfo_am_inc) < 0) || (SMR_DW_UINT(m, &chip->lfo_pm_cnt) < 0) || (SMR_DW_UINT(m, &chip->lfo_pm_inc) < 0) || (SMR_DW_UINT(m, &chip->noise_rng) < 0) || (SMR_DW_UINT(m, &chip->noise_p) < 0) || (SMR_DW_UINT(m, &chip->noise_f) < 0) || (SMR_B(m, &chip->wavesel) < 0) || (SMR_DW_UINT(m, &chip->T[0]) < 0) || (SMR_DW_UINT(m, &chip->T[1]) < 0) || (SMR_B(m, &chip->st[0]) < 0) || (SMR_B(m, &chip->st[1]) < 0) || (SMR_B(m, &chip->type) < 0) || (SMR_B(m, &chip->address) < 0) || (SMR_B(m, &chip->status) < 0) || (SMR_B(m, &chip->statusmask) < 0) || (SMR_B(m, &chip->mode) < 0) || (SMR_DW_UINT(m, &chip->clock) < 0) || (SMR_DW_UINT(m, &chip->rate) < 0) || (SMR_DB(m, &chip->freqbase) < 0)) { snapshot_module_close(m); return -1; } snapshot_module_close(m); return 0; }
int vicii_snapshot_read_module(snapshot_t *s) { BYTE major_version, minor_version; int i; snapshot_module_t *m; BYTE color_ram[0x400]; m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) { return -1; } if (major_version > SNAP_MAJOR || minor_version > SNAP_MINOR) { log_error(vicii.log, "Snapshot module version (%d.%d) newer than %d.%d.", major_version, minor_version, SNAP_MAJOR, SNAP_MINOR); goto fail; } /* FIXME: initialize changes? */ if (0 /* AllowBadLines */ || SMR_B_INT(m, &vicii.allow_bad_lines) < 0 /* BadLine */ || SMR_B_INT(m, &vicii.bad_line) < 0 /* Blank */ || SMR_B_INT(m, &vicii.raster.blank_enabled) < 0 /* ColorBuf */ || SMR_BA(m, vicii.cbuf, 40) < 0 /* ColorRam */ || SMR_BA(m, color_ram, 1024) < 0 /* IdleState */ || SMR_B_INT(m, &vicii.idle_state) < 0 /* LPTrigger */ || SMR_B_INT(m, &vicii.light_pen.triggered) < 0 /* LPX */ || SMR_B_INT(m, &vicii.light_pen.x) < 0 /* LPY */ || SMR_B_INT(m, &vicii.light_pen.y) < 0 /* MatrixBuf */ || SMR_BA(m, vicii.vbuf, 40) < 0 /* NewSpriteDmaMask */ || SMR_B(m, &vicii.raster.sprite_status->new_dma_msk) < 0) { goto fail; } mem_color_ram_from_snapshot(color_ram); { DWORD RamBase; if (SMR_DW(m, &RamBase) < 0) { goto fail; } vicii.ram_base_phi1 = mem_ram + RamBase; } /* Read the current raster line and the current raster cycle. As they are a function of `clk', this is just a sanity check. */ { WORD RasterLine; BYTE RasterCycle; if (SMR_B(m, &RasterCycle) < 0 || SMR_W(m, &RasterLine) < 0) { goto fail; } if (RasterCycle != (BYTE)VICII_RASTER_CYCLE(maincpu_clk)) { log_error(vicii.log, "Not matching raster cycle (%d) in snapshot; should be %d.", RasterCycle, VICII_RASTER_CYCLE(maincpu_clk)); goto fail; } if (RasterLine != (WORD)VICII_RASTER_Y(maincpu_clk)) { log_error(vicii.log, "VIC-II: Not matching raster line (%d) in snapshot; should be %d.", RasterLine, VICII_RASTER_Y(maincpu_clk)); goto fail; } } for (i = 0; i < 0x40; i++) { if (SMR_B(m, &vicii.regs[i]) < 0 /* Registers */) { goto fail; } } if (0 /* SbCollMask */ || SMR_B(m, &vicii.sprite_background_collisions) < 0 /* SpriteDmaMask */ || SMR_B(m, &vicii.raster.sprite_status->dma_msk) < 0 /* SsCollMask */ || SMR_B(m, &vicii.sprite_sprite_collisions) < 0 /* VBank */ || SMR_W_INT(m, &vicii.vbank_phi1) < 0 /* Vc */ || SMR_W_INT(m, &vicii.mem_counter) < 0 /* VcInc */ || SMR_B_INT(m, &vicii.mem_counter_inc) < 0 /* VcBase */ || SMR_W_INT(m, &vicii.memptr) < 0 /* VideoInt */ || SMR_B_INT(m, &vicii.irq_status) < 0) { goto fail; } for (i = 0; i < 8; i++) { if (0 /* SpriteXMemPtr */ || SMR_B_INT(m, &vicii.raster.sprite_status->sprites[i].memptr) < 0 /* SpriteXMemPtrInc */ || SMR_B_INT(m, &vicii.raster.sprite_status->sprites[i].memptr_inc) < 0 /* SpriteXExpFlipFlop */ || SMR_B_INT(m, &vicii.raster.sprite_status->sprites[i].exp_flag) < 0 ) { goto fail; } } /* FIXME: Recalculate alarms and derived values. */ #if 1 { /* We cannot use vicii_irq_set_raster_line as this would delay an alarm on line 0 for one frame */ unsigned int line = vicii.regs[0x12] | ((vicii.regs[0x11] & 0x80) << 1); if (line < (unsigned int)vicii.screen_height) { vicii.raster_irq_clk = (VICII_LINE_START_CLK(maincpu_clk) + VICII_RASTER_IRQ_DELAY - INTERRUPT_DELAY + (vicii.cycles_per_line * line)); /* Raster interrupts on line 0 are delayed by 1 cycle. */ if (line == 0) { vicii.raster_irq_clk++; } alarm_set(vicii.raster_irq_alarm, vicii.raster_irq_clk); } else { vicii.raster_irq_clk = CLOCK_MAX; alarm_unset(vicii.raster_irq_alarm); } vicii.raster_irq_line = line; } #else vicii_irq_set_raster_line(vicii.regs[0x12] | ((vicii.regs[0x11] & 0x80) << 1)); #endif /* compatibility with older versions */ vicii.ram_base_phi2 = vicii.ram_base_phi1; vicii.vbank_phi2 = vicii.vbank_phi1; vicii_update_memory_ptrs(VICII_RASTER_CYCLE(maincpu_clk)); /* Update sprite parameters. We had better do this manually, or the VIC-II emulation could be quite upset. */ { BYTE msk; for (i = 0, msk = 0x1; i < 8; i++, msk <<= 1) { raster_sprite_t *sprite; int tmp; sprite = vicii.raster.sprite_status->sprites + i; /* X/Y coordinates. */ tmp = vicii.regs[i * 2] + ((vicii.regs[0x10] & msk) ? 0x100 : 0); /* (-0xffff makes sure it's updated NOW.) */ vicii_sprites_set_x_position(i, tmp, -0xffff); sprite->y = (int)vicii.regs[i * 2 + 1]; sprite->x_expanded = (int)(vicii.regs[0x1d] & msk); sprite->y_expanded = (int)(vicii.regs[0x17] & msk); sprite->multicolor = (int)(vicii.regs[0x1c] & msk); sprite->in_background = (int)(vicii.regs[0x1b] & msk); sprite->color = (int) vicii.regs[0x27 + i] & 0xf; sprite->dma_flag = (int)(vicii.raster.sprite_status->new_dma_msk & msk); } } vicii.sprite_fetch_msk = vicii.raster.sprite_status->new_dma_msk; vicii.sprite_fetch_clk = VICII_LINE_START_CLK(maincpu_clk) + vicii.sprite_fetch_cycle - vicii.cycles_per_line; /* calculate the sprite_fetch_idx */ { const vicii_sprites_fetch_t *sf; sf = vicii_sprites_fetch_table[vicii.sprite_fetch_msk]; i = 0; while (sf[i].cycle >= 0 && sf[i].cycle + vicii.sprite_fetch_cycle <= vicii.cycles_per_line) { i++; } vicii.sprite_fetch_idx = i; } vicii.raster.xsmooth = vicii.regs[0x16] & 0x7; vicii.raster.sprite_xsmooth = vicii.regs[0x16] & 0x7; vicii.raster.ysmooth = vicii.regs[0x11] & 0x7; vicii.raster.current_line = VICII_RASTER_Y(maincpu_clk); /* FIXME? */ vicii.raster.sprite_status->visible_msk = vicii.regs[0x15]; /* Update colors. */ vicii.raster.border_color = vicii.regs[0x20] & 0xf; vicii.raster.background_color = vicii.regs[0x21] & 0xf; vicii.ext_background_color[0] = vicii.regs[0x22] & 0xf; vicii.ext_background_color[1] = vicii.regs[0x23] & 0xf; vicii.ext_background_color[2] = vicii.regs[0x24] & 0xf; vicii.raster.sprite_status->mc_sprite_color_1 = vicii.regs[0x25] & 0xf; vicii.raster.sprite_status->mc_sprite_color_2 = vicii.regs[0x26] & 0xf; vicii.raster.blank = !(vicii.regs[0x11] & 0x10); if (VICII_IS_ILLEGAL_MODE(vicii.raster.video_mode)) { vicii.raster.idle_background_color = 0; vicii.force_black_overscan_background_color = 1; } else { vicii.raster.idle_background_color = vicii.raster.background_color; vicii.force_black_overscan_background_color = 0; } if (vicii.regs[0x11] & 0x8) { vicii.raster.display_ystart = vicii.row_25_start_line; vicii.raster.display_ystop = vicii.row_25_stop_line; } else { vicii.raster.display_ystart = vicii.row_24_start_line; vicii.raster.display_ystop = vicii.row_24_stop_line; } if (vicii.regs[0x16] & 0x8) { vicii.raster.display_xstart = VICII_40COL_START_PIXEL; vicii.raster.display_xstop = VICII_40COL_STOP_PIXEL; } else { vicii.raster.display_xstart = VICII_38COL_START_PIXEL; vicii.raster.display_xstop = VICII_38COL_STOP_PIXEL; } /* `vicii.raster.draw_idle_state', `vicii.raster.open_right_border' and `vicii.raster.open_left_border' should be needed, but they would only affect the current vicii.raster line, and would not cause any difference in timing. So who cares. */ /* FIXME: `vicii.ycounter_reset_checked'? */ /* FIXME: `vicii.force_display_state'? */ vicii.memory_fetch_done = 0; /* FIXME? */ vicii_update_video_mode(VICII_RASTER_CYCLE(maincpu_clk)); vicii.draw_clk = maincpu_clk + (vicii.draw_cycle - VICII_RASTER_CYCLE(maincpu_clk)); vicii.last_emulate_line_clk = vicii.draw_clk - vicii.cycles_per_line; alarm_set(vicii.raster_draw_alarm, vicii.draw_clk); { DWORD dw; BYTE b; if (0 || SMR_DW(m, &dw) < 0 /* FetchEventTick */ || SMR_B(m, &b) < 0 /* FetchEventType */ ) { goto fail; } vicii.fetch_clk = maincpu_clk + dw; vicii.fetch_idx = b; alarm_set(vicii.raster_fetch_alarm, vicii.fetch_clk); } if (vicii.irq_status & 0x80) { interrupt_restore_irq(maincpu_int_status, vicii.int_num, 1); } /* added in version 1.1 of snapshot format */ if (minor_version > 0) { DWORD RamBase; if (0 || SMR_DW(m, &RamBase) < 0 || SMR_W_INT(m, &vicii.vbank_phi2) < 0 /* VBank */ ) { goto fail; } vicii.ram_base_phi2 = mem_ram + RamBase; vicii_update_memory_ptrs(VICII_RASTER_CYCLE(maincpu_clk)); } raster_force_repaint(&vicii.raster); snapshot_module_close(m); return 0; fail: if (m != NULL) { snapshot_module_close(m); } return -1; }
int drive_snapshot_read_module(snapshot_t *s) { BYTE major_version, minor_version; int i; snapshot_module_t *m; char snap_module_name[] = "DRIVE"; DWORD rotation_table_ptr[DRIVE_NUM]; CLOCK attach_clk[DRIVE_NUM]; CLOCK detach_clk[DRIVE_NUM]; CLOCK attach_detach_clk[DRIVE_NUM]; int drive_true_emulation; int sync_factor; drive_t *drive; int dummy; int half_track[DRIVE_NUM]; m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) { /* If this module is not found true emulation is off. */ resources_set_int("DriveTrueEmulation", 0); return 0; } drive_gcr_data_writeback_all(); if (major_version > DRIVE_SNAP_MAJOR || minor_version > DRIVE_SNAP_MINOR) { log_error(drive_snapshot_log, "Snapshot module version (%d.%d) newer than %d.%d.", major_version, minor_version, DRIVE_SNAP_MAJOR, DRIVE_SNAP_MINOR); } /* If this module exists true emulation is enabled. */ /* XXX drive_true_emulation = 1 */ resources_set_int("DriveTrueEmulation", 1); if (SMR_DW_INT(m, &sync_factor) < 0) { snapshot_module_close(m); return -1; } /* TODO: NUM_DRIVES drives instead of 2 */ for (i = 0; i < 2; i++) { drive = drive_context[i]->drive; /* Partially read 1.0 snapshots */ if (major_version == 1 && minor_version == 0) { if (0 || SMR_DW_UL(m, &(drive->snap_accum)) < 0 || SMR_DW(m, &(attach_clk[i])) < 0 || SMR_DW_INT(m, &dummy) < 0 || SMR_B_INT(m, (int *)&(drive->byte_ready_level)) < 0 || SMR_B_INT(m, &(drive->clock_frequency)) < 0 || SMR_W_INT(m, &half_track[i]) < 0 || SMR_DW(m, &(detach_clk[i])) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B_INT(m, &(drive->extend_image_policy)) < 0 || SMR_B_INT(m, &dummy) < 0 || SMR_DW_UINT(m, &(drive->GCR_head_offset)) < 0 || SMR_B(m, &(drive->GCR_read)) < 0 || SMR_B(m, &(drive->GCR_write_value)) < 0 || SMR_B_INT(m, &(drive->idling_method)) < 0 || SMR_B_INT(m, &dummy) < 0 || SMR_B_INT(m, &(drive->parallel_cable)) < 0 || SMR_B_INT(m, &(drive->read_only)) < 0 || SMR_DW(m, &(drive->snap_rotation_last_clk)) < 0 || SMR_DW(m, &rotation_table_ptr[i]) < 0 || SMR_DW_UINT(m, &(drive->type)) < 0 ) { snapshot_module_close(m); return -1; } /* Partially read 1.1 snapshots */ } else if (major_version == 1 && minor_version == 1) { if (0 || SMR_DW(m, &(attach_clk[i])) < 0 || SMR_B_INT(m, (int *)&(drive->byte_ready_level)) < 0 || SMR_B_INT(m, &(drive->clock_frequency)) < 0 || SMR_W_INT(m, &half_track[i]) < 0 || SMR_DW(m, &(detach_clk[i])) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B_INT(m, &(drive->extend_image_policy)) < 0 || SMR_DW_UINT(m, &(drive->GCR_head_offset)) < 0 || SMR_B(m, &(drive->GCR_read)) < 0 || SMR_B(m, &(drive->GCR_write_value)) < 0 || SMR_B_INT(m, &(drive->idling_method)) < 0 || SMR_B_INT(m, &(drive->parallel_cable)) < 0 || SMR_B_INT(m, &(drive->read_only)) < 0 || SMR_DW(m, &rotation_table_ptr[i]) < 0 || SMR_DW_UINT(m, &(drive->type)) < 0 || SMR_DW_UL(m, &(drive->snap_accum)) < 0 || SMR_DW(m, &(drive->snap_rotation_last_clk)) < 0 || SMR_DW_INT(m, &(drive->snap_bit_counter)) < 0 || SMR_DW_INT(m, &(drive->snap_zero_count)) < 0 || SMR_W_INT(m, &(drive->snap_last_read_data)) < 0 || SMR_B(m, &(drive->snap_last_write_data)) < 0 || SMR_DW_INT(m, &(drive->snap_seed)) < 0 ) { snapshot_module_close(m); return -1; } /* Partially read 1.2 snapshots */ } else if (major_version == 1 && minor_version == 2) { if (0 || SMR_DW(m, &(attach_clk[i])) < 0 || SMR_B_INT(m, (int *)&(drive->byte_ready_level)) < 0 || SMR_B_INT(m, &(drive->clock_frequency)) < 0 || SMR_W_INT(m, &half_track[i]) < 0 || SMR_DW(m, &(detach_clk[i])) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B_INT(m, &(drive->extend_image_policy)) < 0 || SMR_DW_UINT(m, &(drive->GCR_head_offset)) < 0 || SMR_B(m, &(drive->GCR_read)) < 0 || SMR_B(m, &(drive->GCR_write_value)) < 0 || SMR_B_INT(m, &(drive->idling_method)) < 0 || SMR_B_INT(m, &(drive->parallel_cable)) < 0 || SMR_B_INT(m, &(drive->read_only)) < 0 || SMR_DW(m, &rotation_table_ptr[i]) < 0 || SMR_DW_UINT(m, &(drive->type)) < 0 || SMR_DW_UL(m, &(drive->snap_accum)) < 0 || SMR_DW(m, &(drive->snap_rotation_last_clk)) < 0 || SMR_DW_INT(m, &(drive->snap_bit_counter)) < 0 || SMR_DW_INT(m, &(drive->snap_zero_count)) < 0 || SMR_W_INT(m, &(drive->snap_last_read_data)) < 0 || SMR_B(m, &(drive->snap_last_write_data)) < 0 || SMR_DW_INT(m, &(drive->snap_seed)) < 0 || SMR_DW(m, &(drive->snap_speed_zone)) < 0 || SMR_DW(m, &(drive->snap_ue7_dcba)) < 0 || SMR_DW(m, &(drive->snap_ue7_counter)) < 0 || SMR_DW(m, &(drive->snap_uf4_counter)) < 0 || SMR_DW(m, &(drive->snap_fr_randcount)) < 0 || SMR_DW(m, &(drive->snap_filter_counter)) < 0 || SMR_DW(m, &(drive->snap_filter_state)) < 0 || SMR_DW(m, &(drive->snap_filter_last_state)) < 0 || SMR_DW(m, &(drive->snap_write_flux)) < 0 || SMR_DW(m, &(drive->snap_PulseHeadPosition)) < 0 || SMR_DW(m, &(drive->snap_xorShift32)) < 0 ) { snapshot_module_close(m); return -1; } } else if (major_version == 1 && minor_version == 3) { if (0 || SMR_DW(m, &(attach_clk[i])) < 0 || SMR_B_INT(m, (int *)&(drive->byte_ready_level)) < 0 || SMR_B_INT(m, &(drive->clock_frequency)) < 0 || SMR_W_INT(m, &half_track[i]) < 0 || SMR_DW(m, &(detach_clk[i])) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B_INT(m, &(drive->extend_image_policy)) < 0 || SMR_DW_UINT(m, &(drive->GCR_head_offset)) < 0 || SMR_B(m, &(drive->GCR_read)) < 0 || SMR_B(m, &(drive->GCR_write_value)) < 0 || SMR_B_INT(m, &(drive->idling_method)) < 0 || SMR_B_INT(m, &(drive->parallel_cable)) < 0 || SMR_B_INT(m, &(drive->read_only)) < 0 || SMR_DW(m, &rotation_table_ptr[i]) < 0 || SMR_DW_UINT(m, &(drive->type)) < 0 || SMR_DW_UL(m, &(drive->snap_accum)) < 0 || SMR_DW(m, &(drive->snap_rotation_last_clk)) < 0 || SMR_DW_INT(m, &(drive->snap_bit_counter)) < 0 || SMR_DW_INT(m, &(drive->snap_zero_count)) < 0 || SMR_W_INT(m, &(drive->snap_last_read_data)) < 0 || SMR_B(m, &(drive->snap_last_write_data)) < 0 || SMR_DW_INT(m, &(drive->snap_seed)) < 0 || SMR_DW(m, &(drive->snap_speed_zone)) < 0 || SMR_DW(m, &(drive->snap_ue7_dcba)) < 0 || SMR_DW(m, &(drive->snap_ue7_counter)) < 0 || SMR_DW(m, &(drive->snap_uf4_counter)) < 0 || SMR_DW(m, &(drive->snap_fr_randcount)) < 0 || SMR_DW(m, &(drive->snap_filter_counter)) < 0 || SMR_DW(m, &(drive->snap_filter_state)) < 0 || SMR_DW(m, &(drive->snap_filter_last_state)) < 0 || SMR_DW(m, &(drive->snap_write_flux)) < 0 || SMR_DW(m, &(drive->snap_PulseHeadPosition)) < 0 || SMR_DW(m, &(drive->snap_xorShift32)) < 0 || SMR_DW(m, &(drive->snap_so_delay)) < 0 ) { snapshot_module_close(m); return -1; } } else { if (0 || SMR_DW(m, &(attach_clk[i])) < 0 || SMR_B_INT(m, (int *)&(drive->byte_ready_level)) < 0 || SMR_B_INT(m, &(drive->clock_frequency)) < 0 || SMR_W_INT(m, &half_track[i]) < 0 || SMR_DW(m, &(detach_clk[i])) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B(m, (BYTE *)&dummy) < 0 || SMR_B_INT(m, &(drive->extend_image_policy)) < 0 || SMR_DW_UINT(m, &(drive->GCR_head_offset)) < 0 || SMR_B(m, &(drive->GCR_read)) < 0 || SMR_B(m, &(drive->GCR_write_value)) < 0 || SMR_B_INT(m, &(drive->idling_method)) < 0 || SMR_B_INT(m, &(drive->parallel_cable)) < 0 || SMR_B_INT(m, &(drive->read_only)) < 0 || SMR_DW(m, &rotation_table_ptr[i]) < 0 || SMR_DW_UINT(m, &(drive->type)) < 0 || SMR_DW_UL(m, &(drive->snap_accum)) < 0 || SMR_DW(m, &(drive->snap_rotation_last_clk)) < 0 || SMR_DW_INT(m, &(drive->snap_bit_counter)) < 0 || SMR_DW_INT(m, &(drive->snap_zero_count)) < 0 || SMR_W_INT(m, &(drive->snap_last_read_data)) < 0 || SMR_B(m, &(drive->snap_last_write_data)) < 0 || SMR_DW_INT(m, &(drive->snap_seed)) < 0 || SMR_DW(m, &(drive->snap_speed_zone)) < 0 || SMR_DW(m, &(drive->snap_ue7_dcba)) < 0 || SMR_DW(m, &(drive->snap_ue7_counter)) < 0 || SMR_DW(m, &(drive->snap_uf4_counter)) < 0 || SMR_DW(m, &(drive->snap_fr_randcount)) < 0 || SMR_DW(m, &(drive->snap_filter_counter)) < 0 || SMR_DW(m, &(drive->snap_filter_state)) < 0 || SMR_DW(m, &(drive->snap_filter_last_state)) < 0 || SMR_DW(m, &(drive->snap_write_flux)) < 0 || SMR_DW(m, &(drive->snap_PulseHeadPosition)) < 0 || SMR_DW(m, &(drive->snap_xorShift32)) < 0 || SMR_DW(m, &(drive->snap_so_delay)) < 0 || SMR_DW(m, &(drive->snap_cycle_index)) < 0 || SMR_DW(m, &(drive->snap_ref_advance)) < 0 || SMR_DW(m, &(drive->snap_req_ref_cycles)) < 0 ) { snapshot_module_close(m); return -1; } } } /* this one is new, so don't test so stay compatible with old snapshots */ for (i = 0; i < 2; i++) { drive = drive_context[i]->drive; SMR_DW(m, &(attach_detach_clk[i])); } /* these are even newer */ for (i = 0; i < 2; i++) { drive = drive_context[i]->drive; SMR_B_INT(m, (int *)&(drive->byte_ready_edge)); SMR_B_INT(m, (int *)&(drive->byte_ready_active)); } snapshot_module_close(m); m = NULL; rotation_table_set(rotation_table_ptr); drive = drive_context[0]->drive; switch (drive->type) { case DRIVE_TYPE_1540: case DRIVE_TYPE_1541: case DRIVE_TYPE_1541II: case DRIVE_TYPE_1551: case DRIVE_TYPE_1570: case DRIVE_TYPE_1571: case DRIVE_TYPE_1571CR: case DRIVE_TYPE_1581: case DRIVE_TYPE_2000: case DRIVE_TYPE_4000: case DRIVE_TYPE_2031: case DRIVE_TYPE_1001: case DRIVE_TYPE_2040: case DRIVE_TYPE_3040: case DRIVE_TYPE_4040: case DRIVE_TYPE_8050: case DRIVE_TYPE_8250: drive->enable = 1; machine_drive_rom_setup_image(0); drivemem_init(drive_context[0], drive->type); resources_set_int("Drive8IdleMethod", drive->idling_method); driverom_initialize_traps(drive); drive_set_active_led_color(drive->type, 0); machine_bus_status_drivetype_set(8, 1); break; case DRIVE_TYPE_NONE: drive_disable(drive_context[0]); machine_bus_status_drivetype_set(8, 0); break; default: return -1; } drive = drive_context[1]->drive; switch (drive->type) { case DRIVE_TYPE_1540: case DRIVE_TYPE_1541: case DRIVE_TYPE_1541II: case DRIVE_TYPE_1551: case DRIVE_TYPE_1570: case DRIVE_TYPE_1571: case DRIVE_TYPE_1581: case DRIVE_TYPE_2000: case DRIVE_TYPE_4000: case DRIVE_TYPE_2031: case DRIVE_TYPE_1001: /* drive 1 does not allow dual disk drive */ drive->enable = 1; machine_drive_rom_setup_image(1); drivemem_init(drive_context[1], drive->type); resources_set_int("Drive9IdleMethod", drive->idling_method); driverom_initialize_traps(drive); drive_set_active_led_color(drive->type, 1); machine_bus_status_drivetype_set(9, 1); break; case DRIVE_TYPE_NONE: case DRIVE_TYPE_8050: case DRIVE_TYPE_8250: drive_disable(drive_context[1]); machine_bus_status_drivetype_set(9, 0); break; default: return -1; } /* Clear parallel cable before undumping parallel port values. */ for (i = 0; i < DRIVE_PC_NUM; i++) { parallel_cable_drive_write(i, 0xff, PARALLEL_WRITE, 0); parallel_cable_drive_write(i, 0xff, PARALLEL_WRITE, 1); } for (i = 0; i < 2; i++) { drive = drive_context[i]->drive; if (drive->enable) { if (drive->type == DRIVE_TYPE_2000 || drive->type == DRIVE_TYPE_4000) { if (drivecpu65c02_snapshot_read_module(drive_context[i], s) < 0) { return -1; } } else { if (drivecpu_snapshot_read_module(drive_context[i], s) < 0) { return -1; } } if (machine_drive_snapshot_read(drive_context[i], s) < 0) { return -1; } } } if (drive_snapshot_read_image_module(s, 0) < 0 || drive_snapshot_read_gcrimage_module(s, 0) < 0 || drive_snapshot_read_p64image_module(s, 0) < 0) { return -1; } if (drive_snapshot_read_image_module(s, 1) < 0 || drive_snapshot_read_gcrimage_module(s, 1) < 0 || drive_snapshot_read_p64image_module(s, 1) < 0) { return -1; } if (driverom_snapshot_read(s, drive_context[0]->drive) < 0) { return -1; } if (driverom_snapshot_read(s, drive_context[1]->drive) < 0) { return -1; } for (i = 0; i < 2; i++) { drive = drive_context[i]->drive; if (drive->type != DRIVE_TYPE_NONE) { drive_enable(drive_context[i]); drive->attach_clk = attach_clk[i]; drive->detach_clk = detach_clk[i]; drive->attach_detach_clk = attach_detach_clk[i]; } } for (i = 0; i < 2; i++) { int side = 0; drive = drive_context[i]->drive; if (drive->type == DRIVE_TYPE_1570 || drive->type == DRIVE_TYPE_1571 || drive->type == DRIVE_TYPE_1571CR) { if (half_track[i] > (DRIVE_HALFTRACKS_1571 + 1)) { side = 1; half_track[i] -= DRIVE_HALFTRACKS_1571; } } drive_set_half_track(half_track[i], side, drive); resources_set_int("MachineVideoStandard", sync_factor); } /* stop currently active drive sounds (bug #3539422) * FIXME: when the drive sound emulation becomes more precise, we might * want/need to save a snapshot of its current state too */ drive_sound_stop(); iec_update_ports_embedded(); drive_update_ui_status(); resources_get_int("DriveTrueEmulation", &drive_true_emulation); if (vdrive_snapshot_module_read(s, drive_true_emulation ? 10 : 8) < 0) { return -1; } return 0; }
int vic_snapshot_read_module(snapshot_t *s) { WORD i; snapshot_module_t *m; BYTE major_version, minor_version; WORD w; BYTE b; sound_close(); m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) { return -1; } if (major_version > SNAP_MAJOR || minor_version > SNAP_MINOR) { log_error(vic.log, "Snapshot module version (%d.%d) newer than %d.%d.", major_version, minor_version, SNAP_MAJOR, SNAP_MINOR); goto fail; } if (SMR_B(m, &b) < 0) { goto fail; } if (b != VIC_RASTER_CYCLE(maincpu_clk)) { log_error(vic.log, "Cycle value (%d) incorrect; should be %d.", (int)b, VIC_RASTER_CYCLE(maincpu_clk)); goto fail; } vic.raster_cycle = (unsigned int)b; if (SMR_W(m, &w) < 0) { goto fail; } if (w != VIC_RASTER_Y(maincpu_clk)) { log_error(vic.log, "Raster line value (%d) incorrect; should be %d.", (int)w, VIC_RASTER_Y(maincpu_clk)); goto fail; } if (SMR_W(m, &w) < 0) { goto fail; } vic.area = (vic_area_state_t)w; if (SMR_W(m, &w) < 0) { goto fail; } vic.fetch_state = (vic_fetch_state_t)w; if (0 || (SMR_DW_UINT(m, &vic.raster_line) < 0) || (SMR_DW_UINT(m, &vic.text_cols) < 0) || (SMR_DW_UINT(m, &vic.text_lines) < 0) || (SMR_DW_UINT(m, &vic.pending_text_cols) < 0) || (SMR_DW_UINT(m, &vic.line_was_blank) < 0) || (SMR_DW_UINT(m, &vic.memptr) < 0) || (SMR_DW_UINT(m, &vic.memptr_inc) < 0) || (SMR_DW_UINT(m, &vic.row_counter) < 0) || (SMR_DW_UINT(m, &vic.buf_offset) < 0) || SMR_B_INT(m, &vic.light_pen.state) < 0 || SMR_B_INT(m, &vic.light_pen.triggered) < 0 || SMR_DW_INT(m, &vic.light_pen.x) < 0 || SMR_DW_INT(m, &vic.light_pen.y) < 0 || SMR_DW_INT(m, &vic.light_pen.x_extra_bits) < 0 || SMR_DW(m, &vic.light_pen.trigger_cycle) < 0 || (SMR_B(m, &vic.vbuf) < 0)) { goto fail; } /* Color RAM. */ if (SMR_BA(m, mem_ram + 0x9400, 0x400) < 0) { goto fail; } for (i = 0; i < 0x10; i++) { if (SMR_B(m, &b) < 0) { goto fail; } /* XXX: This assumes that there are no side effects. */ vic_store(i, b); } raster_force_repaint(&vic.raster); return snapshot_module_close(m); fail: if (m != NULL) snapshot_module_close(m); return -1; }
int ted_snapshot_read_module(snapshot_t *s) { BYTE major_version, minor_version; int i; snapshot_module_t *m; m = snapshot_module_open(s, snap_module_name, &major_version, &minor_version); if (m == NULL) { return -1; } if (major_version > SNAP_MAJOR || minor_version > SNAP_MINOR) { log_error(ted.log, "Snapshot module version (%d.%d) newer than %d.%d.", major_version, minor_version, SNAP_MAJOR, SNAP_MINOR); goto fail; } /* FIXME: initialize changes? */ if (0 || SMR_DW(m, &ted.last_emulate_line_clk) < 0 /* AllowBadLines */ || SMR_B_INT(m, &ted.allow_bad_lines) < 0 /* BadLine */ || SMR_B_INT(m, &ted.bad_line) < 0 /* Blank */ || SMR_B_INT(m, &ted.raster.blank_enabled) < 0 /* ColorBuf */ || SMR_BA(m, ted.cbuf, 40) < 0 /* IdleState */ || SMR_B_INT(m, &ted.idle_state) < 0 /* MatrixBuf */ || SMR_BA(m, ted.vbuf, 40) < 0 ) { goto fail; } /* Read the current raster line and the current raster cycle. As they are a function of `clk', this is just a sanity check. */ { WORD RasterLine; BYTE RasterCycle; if (SMR_B(m, &RasterCycle) < 0 || SMR_W(m, &RasterLine) < 0) { goto fail; } DBG(("TED read snapshot at clock: %d cycle: %d (%d) tedline: %d (%d) rasterline: %d\n", maincpu_clk, TED_RASTER_CYCLE(maincpu_clk), RasterCycle, TED_RASTER_Y(maincpu_clk), RasterLine, ted.raster.current_line)); if (RasterCycle != (BYTE)TED_RASTER_CYCLE(maincpu_clk)) { log_error(ted.log, "Not matching raster cycle (%d) in snapshot; should be %d.", RasterCycle, TED_RASTER_CYCLE(maincpu_clk)); goto fail; } if (RasterLine != (WORD)TED_RASTER_Y(maincpu_clk)) { log_error(ted.log, "Not matching raster line (%d) in snapshot; should be %d.", RasterLine, TED_RASTER_Y(maincpu_clk)); goto fail; } } for (i = 0; i < 0x40; i++) { if (SMR_B(m, &ted.regs[i]) < 0 /* Registers */) { goto fail; } } if (0 || SMR_DW_INT(m, (int*)&ted.ted_raster_counter) < 0 /* Vc */ || SMR_W_INT(m, &ted.mem_counter) < 0 /* VcInc */ || SMR_B_INT(m, &ted.mem_counter_inc) < 0 /* VcBase */ || SMR_W_INT(m, &ted.memptr) < 0 /* VideoInt */ || SMR_B_INT(m, &ted.irq_status) < 0) { goto fail; } /* FIXME: Recalculate alarms and derived values. */ ted_irq_set_raster_line(ted.regs[0x0b] | ((ted.regs[0x0a] & 1) << 8)); ted_update_memory_ptrs(TED_RASTER_CYCLE(maincpu_clk)); ted.raster.xsmooth = ted.regs[0x07] & 0x7; ted.raster.ysmooth = ted.regs[0x06] & 0x7; ted.raster.current_line = TED_RASTER_Y(maincpu_clk); /* FIXME? */ /* Update colors. */ ted.raster.border_color = ted.regs[0x19]; ted.raster.background_color = ted.regs[0x15]; ted.ext_background_color[0] = ted.regs[0x16]; ted.ext_background_color[1] = ted.regs[0x17]; ted.ext_background_color[2] = ted.regs[0x18]; ted.raster.blank = !(ted.regs[0x06] & 0x10); if (TED_IS_ILLEGAL_MODE (ted.raster.video_mode)) { ted.raster.idle_background_color = 0; ted.force_black_overscan_background_color = 1; } else { ted.raster.idle_background_color = ted.raster.background_color; ted.force_black_overscan_background_color = 0; } if (ted.regs[0x06] & 0x8) { ted.raster.display_ystart = ted.row_25_start_line; ted.raster.display_ystop = ted.row_25_stop_line; } else { ted.raster.display_ystart = ted.row_24_start_line; ted.raster.display_ystop = ted.row_24_stop_line; } if (ted.regs[0x07] & 0x8) { ted.raster.display_xstart = TED_40COL_START_PIXEL; ted.raster.display_xstop = TED_40COL_STOP_PIXEL; } else { ted.raster.display_xstart = TED_38COL_START_PIXEL; ted.raster.display_xstop = TED_38COL_STOP_PIXEL; } /* `ted.raster.draw_idle_state', `ted.raster.open_right_border' and `ted.raster.open_left_border' should be needed, but they would only affect the current ted.raster line, and would not cause any difference in timing. So who cares. */ /* FIXME: `ted.ycounter_reset_checked'? */ /* FIXME: `ted.force_display_state'? */ ted.memory_fetch_done = 0; /* FIXME? */ ted_update_video_mode(TED_RASTER_CYCLE(maincpu_clk)); ted.draw_clk = maincpu_clk + (ted.draw_cycle - TED_RASTER_CYCLE(maincpu_clk)); ted.last_emulate_line_clk = ted.draw_clk - ted.cycles_per_line; alarm_set(ted.raster_draw_alarm, ted.draw_clk); { DWORD dw; if (SMR_DW(m, &dw) < 0) { /* FetchEventTick */ goto fail; } ted.fetch_clk = maincpu_clk + dw; alarm_set(ted.raster_fetch_alarm, ted.fetch_clk); } if (ted.irq_status & 0x80) { interrupt_restore_irq(maincpu_int_status, ted.int_num, 1); } raster_force_repaint(&ted.raster); DBG(("TED: snapshot loaded.\n")); return 0; fail: if (m != NULL) { snapshot_module_close(m); } log_error(ted.log, "could not load TED snapshot."); return -1; }