INLINE void remove_device(device_config **listheadptr, const char *tag) { device_config *device = (device_config *)device_list_find_by_tag(*listheadptr, tag); device_custom_config_func custom; assert(device != NULL); /* call the custom config free function first */ custom = (device_custom_config_func)devtype_get_info_fct(device->type, DEVINFO_FCT_CUSTOM_CONFIG); if (custom != NULL) (*custom)(device, MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_FREE, NULL); /* remove the device from the list */ device_list_remove(listheadptr, tag); }
void tms34061_start(running_machine *machine, const struct tms34061_interface *interface) { /* reset the data */ memset(&tms34061, 0, sizeof(tms34061)); tms34061.intf = *interface; tms34061.screen = device_list_find_by_tag(machine->config->devicelist, VIDEO_SCREEN, tms34061.intf.screen_tag); tms34061.vrammask = tms34061.intf.vramsize - 1; /* allocate memory for VRAM */ tms34061.vram = auto_malloc(tms34061.intf.vramsize + 256 * 2); memset(tms34061.vram, 0, tms34061.intf.vramsize + 256 * 2); /* allocate memory for latch RAM */ tms34061.latchram = auto_malloc(tms34061.intf.vramsize + 256 * 2); memset(tms34061.latchram, 0, tms34061.intf.vramsize + 256 * 2); /* add some buffer space for VRAM and latch RAM */ tms34061.vram += 256; tms34061.latchram += 256; /* point the shift register to the base of VRAM for now */ tms34061.shiftreg = tms34061.vram; /* initialize registers to their default values from the manual */ tms34061.regs[TMS34061_HORENDSYNC] = 0x0010; tms34061.regs[TMS34061_HORENDBLNK] = 0x0020; tms34061.regs[TMS34061_HORSTARTBLNK] = 0x01f0; tms34061.regs[TMS34061_HORTOTAL] = 0x0200; tms34061.regs[TMS34061_VERENDSYNC] = 0x0004; tms34061.regs[TMS34061_VERENDBLNK] = 0x0010; tms34061.regs[TMS34061_VERSTARTBLNK] = 0x00f0; tms34061.regs[TMS34061_VERTOTAL] = 0x0100; tms34061.regs[TMS34061_DISPUPDATE] = 0x0000; tms34061.regs[TMS34061_DISPSTART] = 0x0000; tms34061.regs[TMS34061_VERINT] = 0x0000; tms34061.regs[TMS34061_CONTROL1] = 0x7000; tms34061.regs[TMS34061_CONTROL2] = 0x0600; tms34061.regs[TMS34061_STATUS] = 0x0000; tms34061.regs[TMS34061_XYOFFSET] = 0x0010; tms34061.regs[TMS34061_XYADDRESS] = 0x0000; tms34061.regs[TMS34061_DISPADDRESS] = 0x0000; tms34061.regs[TMS34061_VERCOUNTER] = 0x0000; /* start vertical interrupt timer */ tms34061.timer = timer_alloc(tms34061_interrupt, NULL); }
static TIMER_CALLBACK( scanline_timer_device_timer_callback ) { int next_vpos; const device_config *timer = ptr; timer_state *state = get_safe_token(timer); timer_config *config = timer->inline_config; /* get the screen device and verify it */ const device_config *screen = device_list_find_by_tag(timer->machine->config->devicelist, VIDEO_SCREEN, config->screen); assert(screen != NULL); /* first time, start with the first scanline, but do not call the callback */ if (state->first_time) { next_vpos = config->first_vpos; /* indicate that we are done with the first call */ state->first_time = FALSE; } /* not the first time */ else { int vpos = video_screen_get_vpos(screen); /* call the real callback */ config->callback(timer, state->ptr, vpos); /* if the increment is 0 or the next scanline is larger than the screen size, go back to the first one */ if ((config->increment == 0) || ((vpos + config->increment) >= video_screen_get_height(screen))) next_vpos = config->first_vpos; /* otherwise, increment */ else next_vpos = vpos + config->increment; } /* adjust the timer */ timer_adjust_oneshot(state->timer, video_screen_get_time_until_pos(screen, next_vpos, 0), 0); }
INLINE speaker_info *find_speaker_by_tag(const char *tag) { const device_config *speaker = device_list_find_by_tag(Machine->config->devicelist, SPEAKER_OUTPUT, tag); return (speaker == NULL) ? NULL : speaker->token; }
static void machine_config_detokenize(machine_config *config, const machine_config_token *tokens, const device_config *owner, int depth) { UINT32 entrytype = MCONFIG_TOKEN_INVALID; astring *tempstring = astring_alloc(); device_config *device = NULL; /* loop over tokens until we hit the end */ while (entrytype != MCONFIG_TOKEN_END) { device_custom_config_func custom; int size, offset, bits; UINT32 data32, clock; device_type devtype; const char *tag; UINT64 data64; /* unpack the token from the first entry */ TOKEN_GET_UINT32_UNPACK1(tokens, entrytype, 8); switch (entrytype) { /* end */ case MCONFIG_TOKEN_END: break; /* including */ case MCONFIG_TOKEN_INCLUDE: machine_config_detokenize(config, TOKEN_GET_PTR(tokens, tokenptr), owner, depth + 1); break; /* device management */ case MCONFIG_TOKEN_DEVICE_ADD: TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT64_UNPACK2(tokens, entrytype, 8, clock, 32); devtype = TOKEN_GET_PTR(tokens, devtype); tag = TOKEN_GET_STRING(tokens); device = device_list_add(&config->devicelist, owner, devtype, device_build_tag(tempstring, owner, tag), clock); break; case MCONFIG_TOKEN_DEVICE_REMOVE: tag = TOKEN_GET_STRING(tokens); remove_device(&config->devicelist, device_build_tag(tempstring, owner, tag)); device = NULL; break; case MCONFIG_TOKEN_DEVICE_MODIFY: tag = TOKEN_GET_STRING(tokens); device = (device_config *)device_list_find_by_tag(config->devicelist, device_build_tag(tempstring, owner, tag)); if (device == NULL) fatalerror("Unable to find device: tag=%s\n", astring_c(tempstring)); break; case MCONFIG_TOKEN_DEVICE_CLOCK: assert(device != NULL); TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT64_UNPACK2(tokens, entrytype, 8, device->clock, 32); break; case MCONFIG_TOKEN_DEVICE_MAP: assert(device != NULL); TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT32_UNPACK2(tokens, entrytype, 8, data32, 8); device->address_map[data32] = TOKEN_GET_PTR(tokens, addrmap); break; case MCONFIG_TOKEN_DEVICE_CONFIG: assert(device != NULL); device->static_config = TOKEN_GET_PTR(tokens, voidptr); break; case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_1: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_2: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_3: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_4: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_5: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_6: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_7: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_8: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_9: case MCONFIG_TOKEN_DEVICE_CONFIG_CUSTOM_FREE: assert(device != NULL); custom = (device_custom_config_func)devtype_get_info_fct(device->type, DEVINFO_FCT_CUSTOM_CONFIG); assert(custom != NULL); tokens = (*custom)(device, entrytype, tokens); break; case MCONFIG_TOKEN_DEVICE_CONFIG_DATA32: assert(device != NULL); TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT32_UNPACK3(tokens, entrytype, 8, size, 4, offset, 12); data32 = TOKEN_GET_UINT32(tokens); switch (size) { case 1: *(UINT8 *) ((UINT8 *)device->inline_config + offset) = data32; break; case 2: *(UINT16 *)((UINT8 *)device->inline_config + offset) = data32; break; case 4: *(UINT32 *)((UINT8 *)device->inline_config + offset) = data32; break; } break; case MCONFIG_TOKEN_DEVICE_CONFIG_DATA64: assert(device != NULL); TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT32_UNPACK3(tokens, entrytype, 8, size, 4, offset, 12); TOKEN_EXTRACT_UINT64(tokens, data64); switch (size) { case 1: *(UINT8 *) ((UINT8 *)device->inline_config + offset) = data64; break; case 2: *(UINT16 *)((UINT8 *)device->inline_config + offset) = data64; break; case 4: *(UINT32 *)((UINT8 *)device->inline_config + offset) = data64; break; case 8: *(UINT64 *)((UINT8 *)device->inline_config + offset) = data64; break; } break; case MCONFIG_TOKEN_DEVICE_CONFIG_DATAFP32: assert(device != NULL); TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT32_UNPACK4(tokens, entrytype, 8, size, 4, bits, 6, offset, 12); data32 = TOKEN_GET_UINT32(tokens); switch (size) { case 4: *(float *)((UINT8 *)device->inline_config + offset) = (float)(INT32)data32 / (float)(1 << bits); break; case 8: *(double *)((UINT8 *)device->inline_config + offset) = (double)(INT32)data32 / (double)(1 << bits); break; } break; /* core parameters */ case MCONFIG_TOKEN_DRIVER_DATA: TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT32_UNPACK2(tokens, entrytype, 8, config->driver_data_size, 24); break; case MCONFIG_TOKEN_QUANTUM_TIME: TOKEN_EXTRACT_UINT64(tokens, data64); config->minimum_quantum = UINT64_ATTOTIME_TO_ATTOTIME(data64); break; case MCONFIG_TOKEN_QUANTUM_PERFECT_CPU: config->perfect_cpu_quantum = TOKEN_GET_STRING(tokens); break; case MCONFIG_TOKEN_WATCHDOG_VBLANK: TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT32_UNPACK2(tokens, entrytype, 8, config->watchdog_vblank_count, 24); break; case MCONFIG_TOKEN_WATCHDOG_TIME: TOKEN_EXTRACT_UINT64(tokens, data64); config->watchdog_time = UINT64_ATTOTIME_TO_ATTOTIME(data64); break; /* core functions */ case MCONFIG_TOKEN_MACHINE_START: config->machine_start = TOKEN_GET_PTR(tokens, machine_start); break; case MCONFIG_TOKEN_MACHINE_RESET: config->machine_reset = TOKEN_GET_PTR(tokens, machine_reset); break; case MCONFIG_TOKEN_NVRAM_HANDLER: config->nvram_handler = TOKEN_GET_PTR(tokens, nvram_handler); break; case MCONFIG_TOKEN_MEMCARD_HANDLER: config->memcard_handler = TOKEN_GET_PTR(tokens, memcard_handler); break; /* core video parameters */ case MCONFIG_TOKEN_VIDEO_ATTRIBUTES: TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT32_UNPACK2(tokens, entrytype, 8, config->video_attributes, 24); break; case MCONFIG_TOKEN_GFXDECODE: config->gfxdecodeinfo = TOKEN_GET_PTR(tokens, gfxdecode); break; case MCONFIG_TOKEN_PALETTE_LENGTH: TOKEN_UNGET_UINT32(tokens); TOKEN_GET_UINT32_UNPACK2(tokens, entrytype, 8, config->total_colors, 24); break; case MCONFIG_TOKEN_DEFAULT_LAYOUT: config->default_layout = TOKEN_GET_STRING(tokens); break; /* core video functions */ case MCONFIG_TOKEN_PALETTE_INIT: config->init_palette = TOKEN_GET_PTR(tokens, palette_init); break; case MCONFIG_TOKEN_VIDEO_START: config->video_start = TOKEN_GET_PTR(tokens, video_start); break; case MCONFIG_TOKEN_VIDEO_RESET: config->video_reset = TOKEN_GET_PTR(tokens, video_reset); break; case MCONFIG_TOKEN_VIDEO_EOF: config->video_eof = TOKEN_GET_PTR(tokens, video_eof); break; case MCONFIG_TOKEN_VIDEO_UPDATE: config->video_update = TOKEN_GET_PTR(tokens, video_update); break; /* core sound functions */ case MCONFIG_TOKEN_SOUND_START: config->sound_start = TOKEN_GET_PTR(tokens, sound_start); break; case MCONFIG_TOKEN_SOUND_RESET: config->sound_reset = TOKEN_GET_PTR(tokens, sound_reset); break; default: fatalerror("Invalid token %d in machine config\n", entrytype); break; } } /* if we are the outermost level, process any device-specific machine configurations */ if (depth == 0) for (device = config->devicelist; device != NULL; device = device->next) { tokens = (const machine_config_token *)device_get_info_ptr(device, DEVINFO_PTR_MACHINE_CONFIG); if (tokens != NULL) machine_config_detokenize(config, tokens, device, depth + 1); } astring_free(tempstring); }