diff options
author | 2010-08-27 07:21:13 +0000 | |
---|---|---|
committer | 2010-08-27 07:21:13 +0000 | |
commit | 9c6f743089b36ef9dc132f154149dbd02d07b4b3 (patch) | |
tree | 0b6ebffdf89713ec83c4f641780ef8875b03c5ba /src/emu/machine | |
parent | 4cc59054e0f8c95d7429a4792802bd3f0be73aff (diff) |
Updated the PCI bus device so that PCI buses can be arranged in a tree like in real hardware [Samuele Zannoli]
Chihiro.c Improvements: [Samuele Zannoli]
- Fixed the mapping of the bios at the top of the cpu addrsss space
- Updated the ram size to 128 megabytes
- Added some SMBus handling, to let the bios run
- Added placeholders for a few devices on the PCI bus
- Added the "jamdis StartAddress,Length" command to the debugger that lets you disassemble the "jam table" instructions used by the bios to do some basic hardware initialization.
This time it works for good ;)
Diffstat (limited to 'src/emu/machine')
-rw-r--r-- | src/emu/machine/pci.c | 87 | ||||
-rw-r--r-- | src/emu/machine/pci.h | 4 |
2 files changed, 83 insertions, 8 deletions
diff --git a/src/emu/machine/pci.c b/src/emu/machine/pci.c index 4fb5a3989b2..d29599a458f 100644 --- a/src/emu/machine/pci.c +++ b/src/emu/machine/pci.c @@ -81,8 +81,13 @@ struct _pci_bus_state running_device * busdevice; const pci_bus_config * config; running_device * device[32]; + pci_bus_state * siblings[8]; + UINT8 siblings_busnum[8]; + int siblings_count; offs_t address; - INT8 devicenum; + INT8 devicenum; // device number we are addressing + INT8 busnum; // pci bus number we are addressing + pci_bus_state * busnumaddr; // pci bus we are addressing }; @@ -93,7 +98,7 @@ struct _pci_bus_state /*------------------------------------------------- get_safe_token - makes sure that the passed - in device is, in fact, an IDE controller + in device is, in fact, a PCI bus -------------------------------------------------*/ INLINE pci_bus_state *get_safe_token(running_device *device) @@ -123,12 +128,12 @@ READ32_DEVICE_HANDLER( pci_32le_r ) case 1: if (pcibus->devicenum != -1) { - pci_read_func read = pcibus->config->device[pcibus->devicenum].read_callback; + pci_read_func read = pcibus->busnumaddr->config->device[pcibus->devicenum].read_callback; if (read != NULL) { function = (pcibus->address >> 8) & 0x07; reg = (pcibus->address >> 0) & 0xfc; - result = (*read)(device, pcibus->device[pcibus->devicenum], function, reg, mem_mask); + result = (*read)(pcibus->busnumaddr->busdevice, pcibus->busnumaddr->device[pcibus->devicenum], function, reg, mem_mask); } } break; @@ -142,6 +147,26 @@ READ32_DEVICE_HANDLER( pci_32le_r ) +static pci_bus_state *pci_search_bustree(int busnum, int devicenum, pci_bus_state *pcibus) +{ +int a; +pci_bus_state *ret; + + if (pcibus->config->busnum == busnum) + { + return pcibus; + } + for (a = 0; a < pcibus->siblings_count; a++) + { + ret = pci_search_bustree(busnum, devicenum, pcibus->siblings[a]); + if (ret != NULL) + return ret; + } + return NULL; +} + + + WRITE32_DEVICE_HANDLER( pci_32le_w ) { pci_bus_state *pcibus = get_safe_token(device); @@ -161,20 +186,31 @@ WRITE32_DEVICE_HANDLER( pci_32le_w ) { int busnum = (pcibus->address >> 16) & 0xff; int devicenum = (pcibus->address >> 11) & 0x1f; - pcibus->devicenum = (busnum == pcibus->config->busnum) ? devicenum : -1; + pcibus->busnumaddr = pci_search_bustree(busnum, devicenum, pcibus); + if (pcibus->busnumaddr != NULL) + { + pcibus->busnum = busnum; + pcibus->devicenum = devicenum; + } + else + pcibus->devicenum = -1; + if (LOG_PCI) + logerror(" bus:%d device:%d\n", busnum, devicenum); } break; case 1: if (pcibus->devicenum != -1) { - pci_write_func write = pcibus->config->device[pcibus->devicenum].write_callback; + pci_write_func write = pcibus->busnumaddr->config->device[pcibus->devicenum].write_callback; if (write != NULL) { int function = (pcibus->address >> 8) & 0x07; int reg = (pcibus->address >> 0) & 0xfc; - (*write)(device, pcibus->device[pcibus->devicenum], function, reg, data, mem_mask); + (*write)(pcibus->busnumaddr->busdevice, pcibus->busnumaddr->device[pcibus->devicenum], function, reg, data, mem_mask); } + if (LOG_PCI) + logerror(" function:%d register:%d\n", (pcibus->address >> 8) & 0x07, (pcibus->address >> 0) & 0xfc); } break; } @@ -186,13 +222,42 @@ READ64_DEVICE_HANDLER(pci_64be_r) { return read64be_with_32le_device_handler(pci WRITE64_DEVICE_HANDLER(pci_64be_w) { write64be_with_32le_device_handler(pci_32le_w, device, offset, data, mem_mask); } - +int pci_add_sibling( running_machine *machine, char *pcitag, char *sibling ) +{ + running_device *device1 = machine->device(pcitag); + running_device *device2 = machine->device(sibling); + pci_bus_state *pcibus1 = get_safe_token(device1); + pci_bus_state *pcibus2 = get_safe_token(device2); + pci_bus_config *config2; + + if ((device1 == NULL) || (device2 == NULL) || (pcibus1 == NULL) || (pcibus2 == NULL)) + return 0; + if (pcibus1->siblings_count == 8) + return 0; + config2 = (pci_bus_config *)downcast<const legacy_device_config_base &>(device2->baseconfig()).inline_config(); + pcibus1->siblings[pcibus1->siblings_count] = get_safe_token(device2); + pcibus1->siblings_busnum[pcibus1->siblings_count] = config2->busnum; + pcibus1->siblings_count++; + return 1; +} /*************************************************************************** DEVICE INTERFACE ***************************************************************************/ + +static STATE_POSTLOAD( pci_bus_postload ) +{ + pci_bus_state *pcibus = (pci_bus_state *)param; + + if (pcibus->devicenum != -1) + { + pcibus->busnumaddr = pci_search_bustree(pcibus->busnum, pcibus->devicenum, pcibus); + } +} + + /*------------------------------------------------- device start callback -------------------------------------------------*/ @@ -219,9 +284,15 @@ static DEVICE_START( pci_bus ) if (pcibus->config->device[devicenum].devtag != NULL) pcibus->device[devicenum] = device->machine->device(pcibus->config->device[devicenum].devtag); + if (pcibus->config->father != NULL) + pci_add_sibling(device->machine, (char *)pcibus->config->father, (char *)device->tag()); + /* register pci states */ state_save_register_device_item(device, 0, pcibus->address); state_save_register_device_item(device, 0, pcibus->devicenum); + state_save_register_device_item(device, 0, pcibus->busnum); + + state_save_register_postload(device->machine, pci_bus_postload, pcibus); } diff --git a/src/emu/machine/pci.h b/src/emu/machine/pci.h index 7398077cb78..705a07ced35 100644 --- a/src/emu/machine/pci.h +++ b/src/emu/machine/pci.h @@ -32,6 +32,7 @@ struct _pci_bus_config { UINT8 busnum; pci_device_entry device[32]; + const char * father; }; @@ -49,6 +50,8 @@ struct _pci_bus_config MDRV_DEVICE_CONFIG_DATAPTR_ARRAY_MEMBER(pci_bus_config, device, _devnum, pci_device_entry, read_callback, _configread) \ MDRV_DEVICE_CONFIG_DATAPTR_ARRAY_MEMBER(pci_bus_config, device, _devnum, pci_device_entry, write_callback, _configwrite) +#define MDRV_PCI_BUS_SIBLING(_father_tag) \ + MDRV_DEVICE_CONFIG_DATAPTR(pci_bus_config, father, _father_tag) /*************************************************************************** @@ -61,6 +64,7 @@ WRITE32_DEVICE_HANDLER( pci_32le_w ); READ64_DEVICE_HANDLER( pci_64be_r ); WRITE64_DEVICE_HANDLER( pci_64be_w ); +int pci_add_sibling( running_machine *machine, char *pcitag, char *sibling ); /* ----- device interface ----- */ |