diff --git a/src/Makefile.mingw b/src/Makefile.mingw index 63bb51fe0..d63c46706 100644 --- a/src/Makefile.mingw +++ b/src/Makefile.mingw @@ -22,9 +22,7 @@ endif # Various compile-time options. # -DROM_TRACE=0xcd800 traces ROM access from segment C800 # -DIO_TACE=0x66 traces I/O on port 0x66 -ifndef STUFF STUFF = -endif # Add feature selections here. # -DANSI_CFG forces the config file to ANSI encoding. @@ -54,6 +52,9 @@ endif ifndef USB USB = n endif +ifndef DEV_BRANCH +DEV_BRANCH = n +endif ifndef X64 X64 = n endif @@ -248,8 +249,12 @@ WINOBJ = win.o \ win_iodev.o win_joystick.o win_midi.o \ win_settings.o win_deviceconfig.o win_joystickconfig.o \ 86Box.res +ifdef DEV_BRANCH +DEVOBJ = vid_nv_riva128.o +endif OBJ = $(MAINOBJ) $(CPUOBJ) $(SYSOBJ) $(DEVOBJ) $(USBOBJ) \ - $(NETOBJ) $(SCSIOBJ) $(SNDOBJ) $(VIDOBJ) $(WINOBJ) + $(NETOBJ) $(SCSIOBJ) $(SNDOBJ) $(VIDOBJ) $(WINOBJ) \ + $(DEVOBJ) LZFOBJ = lzf_c.o lzf_d.o diff --git a/src/Makefile.mingw64 b/src/Makefile.mingw64 index 2f0f9b408..53efdd58b 100644 --- a/src/Makefile.mingw64 +++ b/src/Makefile.mingw64 @@ -28,6 +28,6 @@ EXTRAS = DEBUG = n OPTIM = n X64 = y - +DEV_BRANCH = n # End of Makefile.mingw64. diff --git a/src/VIDEO/vid_nv_riva128.c b/src/VIDEO/vid_nv_riva128.c index b2504f58c..1bb638e50 100644 --- a/src/VIDEO/vid_nv_riva128.c +++ b/src/VIDEO/vid_nv_riva128.c @@ -29,6 +29,7 @@ typedef struct riva128_t svga_t svga; uint8_t card_id; + int pci_card; int is_nv3t; uint16_t vendor_id; @@ -128,7 +129,7 @@ typedef struct riva128_t struct { - uint32_t boot0; + uint32_t boot_0; } pextdev; struct @@ -212,8 +213,16 @@ typedef struct riva128_t { int scl; int sda; + int busy; + unsigned addrbits; + unsigned databits; uint8_t addr; //actually 7 bits uint8_t data; + struct + { + uint8_t addr; + uint8_t edid_rom[128]; + } edid_rom; } i2c; int mtime, mfreq; @@ -244,18 +253,18 @@ const char* riva128_pfifo_interrupts[32] = "CACHE_ERROR","","","","RUNOUT","","","","RUNOUT_OVERFLOW","","","","DMA_PUSHER","","","","DMA_PTE","","","","","","","","","","","","","","","" }; -static uint32_t riva128_ramht_lookup(uint32_t handle, void *p); -//static void riva128_pgraph_volatile_reset(void *p); + uint32_t riva128_ramht_lookup(uint32_t handle, void *p); +// void riva128_pgraph_volatile_reset(void *p); -static uint8_t riva128_pci_read(int func, int addr, void *p); -static void riva128_pci_write(int func, int addr, uint8_t val, void *p); + uint8_t riva128_pci_read(int func, int addr, void *p); + void riva128_pci_write(int func, int addr, uint8_t val, void *p); -static uint8_t riva128_in(uint16_t addr, void *p); -static void riva128_out(uint16_t addr, uint8_t val, void *p); + uint8_t riva128_in(uint16_t addr, void *p); + void riva128_out(uint16_t addr, uint8_t val, void *p); -static void riva128_mmio_write_l(uint32_t addr, uint32_t val, void *p); + void riva128_mmio_write_l(uint32_t addr, uint32_t val, void *p); -/*static riva128_color_t riva128_pgraph_expand_color(uint32_t ctx, uint32_t color) +/* riva128_color_t riva128_pgraph_expand_color(uint32_t ctx, uint32_t color) { riva128_color_t ret; int format = ctx & 7; @@ -300,7 +309,7 @@ static void riva128_mmio_write_l(uint32_t addr, uint32_t val, void *p); return ret; } -static uint32_t riva128_pgraph_blend_factor(uint32_t alpha, uint32_t beta) + uint32_t riva128_pgraph_blend_factor(uint32_t alpha, uint32_t beta) { if(beta == 0xff) return alpha; if(alpha == 0xff) return beta; @@ -309,7 +318,7 @@ static uint32_t riva128_pgraph_blend_factor(uint32_t alpha, uint32_t beta) return (alpha * beta) >> 1; } -static uint32_t riva128_pgraph_do_blend(uint32_t factor, uint32_t dst, uint32_t src, int is_r5g5b5) + uint32_t riva128_pgraph_do_blend(uint32_t factor, uint32_t dst, uint32_t src, int is_r5g5b5) { factor &= 0xf8; if(factor == 0xf8) return src; @@ -324,7 +333,7 @@ static uint32_t riva128_pgraph_do_blend(uint32_t factor, uint32_t dst, uint32_t return ((dst * (0x100 - factor)) + (src * factor)) >> 6; }*/ -static uint8_t riva128_pmc_read(uint32_t addr, void *p) + uint8_t riva128_pmc_read(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -431,7 +440,7 @@ static uint8_t riva128_pmc_read(uint32_t addr, void *p) return ret; } -static void riva128_pmc_write(uint32_t addr, uint32_t val, void *p) + void riva128_pmc_write(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; //pclog("RIVA 128 PMC write %08X %08X %04X:%08X\n", addr, val, CS, cpu_state.pc); @@ -439,8 +448,12 @@ static void riva128_pmc_write(uint32_t addr, uint32_t val, void *p) switch(addr) { case 0x000100: - riva128->pmc.intr &= ~val; + { + uint32_t tmp = riva128->pmc.intr & ~val; + pci_clear_irq(riva128->pci_card, PCI_INTA); + riva128->pmc.intr = tmp; break; + } case 0x000140: riva128->pmc.intr_en = val & 3; break; @@ -450,17 +463,20 @@ static void riva128_pmc_write(uint32_t addr, uint32_t val, void *p) } } -static void riva128_pmc_interrupt(int num, void *p) + void riva128_pmc_interrupt(int num, void *p) { //pclog("RIVA 128 PMC interrupt #%d fired!\n", num); riva128_t *riva128 = (riva128_t *)p; riva128->pmc.intr |= (1 << num); - if(riva128->pmc.intr_en & 1) picint(1 << riva128->pci_regs[0x3c]); + if(riva128->pmc.intr_en & 1) + { + pci_set_irq(riva128->pci_card, PCI_INTA); + } } -static uint8_t riva128_pbus_read(uint32_t addr, void *p) + uint8_t riva128_pbus_read(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -500,7 +516,7 @@ static uint8_t riva128_pbus_read(uint32_t addr, void *p) return ret; } -static void riva128_pbus_write(uint32_t addr, uint32_t val, void *p) + void riva128_pbus_write(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; //pclog("RIVA 128 PBUS write %08X %08X %04X:%08X\n", addr, val, CS, cpu_state.pc); @@ -524,7 +540,7 @@ static void riva128_pbus_write(uint32_t addr, uint32_t val, void *p) } } -static uint8_t riva128_pfifo_read(uint32_t addr, void *p) + uint8_t riva128_pfifo_read(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -653,7 +669,7 @@ static uint8_t riva128_pfifo_read(uint32_t addr, void *p) return ret; } -static void riva128_pfifo_write(uint32_t addr, uint32_t val, void *p) + void riva128_pfifo_write(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; // pclog("RIVA 128 PFIFO write %08X %08X %04X:%08X\n", addr, val, CS, cpu_state.pc); @@ -713,7 +729,7 @@ static void riva128_pfifo_write(uint32_t addr, uint32_t val, void *p) } } -static void riva128_pfifo_interrupt(int num, void *p) + void riva128_pfifo_interrupt(int num, void *p) { riva128_t *riva128 = (riva128_t *)p; @@ -722,7 +738,7 @@ static void riva128_pfifo_interrupt(int num, void *p) riva128_pmc_interrupt(8, riva128); } -static uint8_t riva128_ptimer_read(uint32_t addr, void *p) + uint8_t riva128_ptimer_read(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -823,7 +839,7 @@ static uint8_t riva128_ptimer_read(uint32_t addr, void *p) return ret; } -static void riva128_ptimer_write(uint32_t addr, uint32_t val, void *p) + void riva128_ptimer_write(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; pclog("RIVA 128 PTIMER write %08X %08X %04X:%08X\n", addr, val, CS, cpu_state.pc); @@ -858,7 +874,7 @@ static void riva128_ptimer_write(uint32_t addr, uint32_t val, void *p) } } -static void riva128_ptimer_interrupt(int num, void *p) + void riva128_ptimer_interrupt(int num, void *p) { //pclog("RIVA 128 PTIMER interrupt #%d fired!\n", num); riva128_t *riva128 = (riva128_t *)p; @@ -868,7 +884,7 @@ static void riva128_ptimer_interrupt(int num, void *p) riva128_pmc_interrupt(20, riva128); } -static uint8_t riva128_pfb_read(uint32_t addr, void *p) + uint8_t riva128_pfb_read(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -937,7 +953,7 @@ static uint8_t riva128_pfb_read(uint32_t addr, void *p) return ret; } -static void riva128_pfb_write(uint32_t addr, uint32_t val, void *p) + void riva128_pfb_write(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; //pclog("RIVA 128 PFB write %08X %08X %04X:%08X\n", addr, val, CS, cpu_state.pc); @@ -963,27 +979,66 @@ static void riva128_pfb_write(uint32_t addr, uint32_t val, void *p) } } -static uint8_t riva128_pextdev_read(uint32_t addr, void *p) +uint8_t riva128_pextdev_read(uint32_t addr, void *p) { - //riva128_t *riva128 = (riva128_t *)p; + riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; //pclog("RIVA 128 PEXTDEV read %08X %04X:%08X\n", addr, CS, cpu_state.pc); + //For NV3, we give it PCI 66MHz, card mode, PCI bus type, 13.5MHz crystal, no TV encoder, and PCI 2.1. + //For NV4, we give it normal PCI line polarity, card mode, 13.5 MHz crystal, no TV encoder, and PCI bus type + switch(addr) { case 0x101000: - ret = 0x9e; + switch(riva128->card_id) + { + case 0x03: + ret = 0x13; + break; + case 0x04: + ret = 0x83; + break; + } break; case 0x101001: - ret = 0x01; + switch(riva128->card_id) + { + case 0x03: + if(!riva128->is_nv3t) ret = 0x02; + else ret = 0x00; + break; + case 0x04: case 0x05: + //Bits 12-13 of the NV4+ strap set 0 configure the GPU's PCI device ID. + ret = (riva128->pextdev.boot_0 & 0x80000000) ? (0x8f | ((riva128->pextdev.boot_0 >> 8) & 0x30)) : 0x8f; + break; break; + } } return ret; } -static void rivatnt_pgraph_ctx_switch(void *p) +void riva128_pextdev_write(uint32_t addr, uint32_t val, void *p) +{ + riva128_t *riva128 = (riva128_t *)p; + //pclog("RIVA 128 PEXTDEV write %08X %08X %04X:%08X\n", addr, val, CS, cpu_state.pc); + + switch(addr) + { + case 0x101000: + riva128->pextdev.boot_0 = val; + if((val & 0x80000000) && ((riva128->card_id == 0x05) || (riva128->card_id == 0x10) || (riva128->card_id == 0x11) || (riva128->card_id == 0x15) + || (riva128->card_id == 0x1a))) + { + riva128->device_id = (riva128->device_id & 0xfffc) | ((val >> 12) & 3); + } + break; + } +} + +void rivatnt_pgraph_ctx_switch(void *p) { riva128_t *riva128 = (riva128_t *)p; @@ -1029,7 +1084,7 @@ static void rivatnt_pgraph_ctx_switch(void *p) } } -static uint8_t riva128_pgraph_read(uint32_t addr, void *p) + uint8_t riva128_pgraph_read(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -1413,7 +1468,7 @@ static uint8_t riva128_pgraph_read(uint32_t addr, void *p) return ret; } -static void riva128_pgraph_write(uint32_t addr, uint32_t val, void *p) + void riva128_pgraph_write(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; pclog("RIVA 128 PGRAPH write %08X %08X %04X:%08X\n", addr, val, CS, cpu_state.pc); @@ -1559,7 +1614,7 @@ static void riva128_pgraph_write(uint32_t addr, uint32_t val, void *p) } } -static void riva128_pgraph_interrupt(int num, void *p) + void riva128_pgraph_interrupt(int num, void *p) { riva128_t *riva128 = (riva128_t *)p; @@ -1568,7 +1623,7 @@ static void riva128_pgraph_interrupt(int num, void *p) riva128_pmc_interrupt(12, riva128); } -static void riva128_pgraph_invalid_interrupt(int num, void *p) + void riva128_pgraph_invalid_interrupt(int num, void *p) { riva128_t *riva128 = (riva128_t *)p; @@ -1577,7 +1632,7 @@ static void riva128_pgraph_invalid_interrupt(int num, void *p) riva128_pgraph_interrupt(0, riva128); } -static uint8_t riva128_pramdac_read(uint32_t addr, void *p) + uint8_t riva128_pramdac_read(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -1651,7 +1706,7 @@ static uint8_t riva128_pramdac_read(uint32_t addr, void *p) return ret; } -static void riva128_pramdac_write(uint32_t addr, uint32_t val, void *p) + void riva128_pramdac_write(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; svga_t* svga = &riva128->svga; @@ -1689,7 +1744,7 @@ static void riva128_pramdac_write(uint32_t addr, uint32_t val, void *p) } } -static uint32_t riva128_ramht_lookup(uint32_t handle, void *p) + uint32_t riva128_ramht_lookup(uint32_t handle, void *p) { riva128_t *riva128 = (riva128_t *)p; uint32_t ramht_base = riva128->pfifo.ramht_addr; @@ -1724,7 +1779,7 @@ static uint32_t riva128_ramht_lookup(uint32_t handle, void *p) return riva128->pramin[ramht_base + (hash * 8)]; } -static void riva128_puller_exec_method(int chanid, int subchanid, int offset, uint32_t val, void *p) + void riva128_puller_exec_method(int chanid, int subchanid, int offset, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; pclog("RIVA 128 Puller executing method %04X on channel %01X[%01X] %04X:%08X\n", offset, chanid, subchanid, val, CS, cpu_state.pc); @@ -1774,7 +1829,7 @@ static void riva128_puller_exec_method(int chanid, int subchanid, int offset, ui } } -static void riva128_pusher_run(int chanid, void *p) + void riva128_pusher_run(int chanid, void *p) { riva128_t *riva128 = (riva128_t *)p; svga_t *svga = &riva128->svga; @@ -1811,7 +1866,7 @@ static void riva128_pusher_run(int chanid, void *p) } } -static void riva128_user_write(uint32_t addr, uint32_t val, void *p) + void riva128_user_write(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; int chanid = (addr >> 16) & 0xf; @@ -1843,7 +1898,7 @@ static void riva128_user_write(uint32_t addr, uint32_t val, void *p) } } -static uint8_t riva128_mmio_read(uint32_t addr, void *p) + uint8_t riva128_mmio_read(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -1879,21 +1934,21 @@ static uint8_t riva128_mmio_read(uint32_t addr, void *p) return ret; } -static uint16_t riva128_mmio_read_w(uint32_t addr, void *p) + uint16_t riva128_mmio_read_w(uint32_t addr, void *p) { addr &= 0xffffff; //pclog("RIVA 128 MMIO read %08X %04X:%08X\n", addr, CS, cpu_state.pc); return (riva128_mmio_read(addr+0,p) << 0) | (riva128_mmio_read(addr+1,p) << 8); } -static uint32_t riva128_mmio_read_l(uint32_t addr, void *p) + uint32_t riva128_mmio_read_l(uint32_t addr, void *p) { addr &= 0xffffff; //pclog("RIVA 128 MMIO read %08X %04X:%08X\n", addr, CS, cpu_state.pc); return (riva128_mmio_read(addr+0,p) << 0) | (riva128_mmio_read(addr+1,p) << 8) | (riva128_mmio_read(addr+2,p) << 16) | (riva128_mmio_read(addr+3,p) << 24); } -static void riva128_mmio_write(uint32_t addr, uint8_t val, void *p) + void riva128_mmio_write(uint32_t addr, uint8_t val, void *p) { addr &= 0xffffff; //pclog("RIVA 128 MMIO write %08X %02X %04X:%08X\n", addr, val, CS, cpu_state.pc); @@ -1910,7 +1965,7 @@ static void riva128_mmio_write(uint32_t addr, uint8_t val, void *p) } } -static void riva128_mmio_write_w(uint32_t addr, uint16_t val, void *p) + void riva128_mmio_write_w(uint32_t addr, uint16_t val, void *p) { uint32_t tmp; addr &= 0xffffff; @@ -1921,7 +1976,7 @@ static void riva128_mmio_write_w(uint32_t addr, uint16_t val, void *p) riva128_mmio_write_l(addr, tmp, p); } -static void riva128_mmio_write_l(uint32_t addr, uint32_t val, void *p) + void riva128_mmio_write_l(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; @@ -1936,6 +1991,7 @@ static void riva128_mmio_write_l(uint32_t addr, uint32_t val, void *p) if((addr >= 0x002000) && (addr <= 0x002fff)) riva128_pfifo_write(addr, val, riva128); if((addr >= 0x009000) && (addr <= 0x009fff)) riva128_ptimer_write(addr, val, riva128); if((addr >= 0x100000) && (addr <= 0x100fff)) riva128_pfb_write(addr, val, riva128); + if((addr >= 0x101000) && (addr <= 0x101fff)) riva128_pextdev_write(addr, val, riva128); if((addr >= 0x400000) && (addr <= 0x400fff)) riva128_pgraph_write(addr, val, riva128); if((addr >= 0x680000) && (addr <= 0x680fff)) riva128_pramdac_write(addr, val, riva128); if((addr >= 0x800000) && (addr <= 0xffffff)) riva128_user_write(addr, val, riva128); @@ -1955,7 +2011,7 @@ static void riva128_mmio_write_l(uint32_t addr, uint32_t val, void *p) } } -static void riva128_ptimer_tick(void *p) + void riva128_ptimer_tick(void *p) { riva128_t *riva128 = (riva128_t *)p; @@ -1977,7 +2033,7 @@ static void riva128_ptimer_tick(void *p) } } -static void riva128_mclk_poll(void *p) + void riva128_mclk_poll(void *p) { riva128_t *riva128 = (riva128_t *)p; @@ -1986,7 +2042,7 @@ static void riva128_mclk_poll(void *p) riva128->mtime += cpuclock / riva128->mfreq; } -static void riva128_nvclk_poll(void *p) + void riva128_nvclk_poll(void *p) { riva128_t *riva128 = (riva128_t *)p; @@ -1995,15 +2051,14 @@ static void riva128_nvclk_poll(void *p) riva128->nvtime += cpuclock / riva128->nvfreq; } -static void riva128_vblank_poll(void *p) + void riva128_vblank_poll(svga_t *svga) { - riva128_t *riva128 = (riva128_t *)p; - svga_t *svga = &riva128->svga; - - if(svga->vc == svga->dispend) riva128_pmc_interrupt(24, riva128); + riva128_t *riva128 = (riva128_t *)svga->p; + + riva128_pmc_interrupt(24, riva128); } -static uint8_t riva128_rma_in(uint16_t addr, void *p) + uint8_t riva128_rma_in(uint16_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -2037,7 +2092,7 @@ static uint8_t riva128_rma_in(uint16_t addr, void *p) return ret; } -static void riva128_rma_out(uint16_t addr, uint8_t val, void *p) + void riva128_rma_out(uint16_t addr, uint8_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; svga_t* svga = &riva128->svga; @@ -2099,7 +2154,7 @@ static void riva128_rma_out(uint16_t addr, uint8_t val, void *p) if(addr & 0x10) riva128->rma.addr+=4; } -static uint8_t riva128_in(uint16_t addr, void *p) + uint8_t riva128_in(uint16_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; svga_t* svga = &riva128->svga; @@ -2126,6 +2181,22 @@ static uint8_t riva128_in(uint16_t addr, void *p) switch(svga->crtcreg) { case 0x3e: + if(riva128->i2c.busy == 2) + { + if(riva128->i2c.addr == 0xA1) + { + //pclog("RIVA 128 Read EDID %02x %02x\n", riva128->i2c.edid_rom.addr, riva128->i2c.edid_rom.edid_rom[riva128->i2c.edid_rom.addr]); + riva128->i2c.data <<= 1; + riva128->i2c.data |= (riva128->i2c.edid_rom.edid_rom[riva128->i2c.edid_rom.addr] & (1 << riva128->i2c.databits)) >> riva128->i2c.databits; + } + riva128->i2c.databits++; + if(riva128->i2c.databits == 8) + { + riva128->i2c.databits = 0; + riva128->i2c.edid_rom.addr++; + riva128->i2c.busy = 0; + } + } ret = (riva128->i2c.sda << 3) | (riva128->i2c.scl << 2); break; case 0x28: @@ -2146,7 +2217,7 @@ static uint8_t riva128_in(uint16_t addr, void *p) return ret; } -static void riva128_out(uint16_t addr, uint8_t val, void *p) + void riva128_out(uint16_t addr, uint8_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; svga_t *svga = &riva128->svga; @@ -2206,8 +2277,44 @@ static void riva128_out(uint16_t addr, uint8_t val, void *p) riva128->rma.mode = val & 0xf; break; case 0x3f: + if((val & 0x20) && (riva128->i2c.sda == 0) && (val & 0x10)) + { + //I2C Start Condition. + riva128->i2c.busy = 1; + } + if((val & 0x20) && (riva128->i2c.sda == 1) && !(val & 0x10)) + { + //I2C Stop Condition. + riva128->i2c.busy = 0; + } riva128->i2c.scl = (val & 0x20) ? 1 : 0; riva128->i2c.sda = (val & 0x10) ? 1 : 0; + if(riva128->i2c.busy == 1) + { + riva128->i2c.addr <<= 1; + riva128->i2c.addr |= riva128->i2c.sda; + riva128->i2c.addrbits++; + if(riva128->i2c.addrbits == 8) + { + riva128->i2c.busy = 2; + riva128->i2c.addrbits = 0; + } + } + if(riva128->i2c.busy == 2) + { + riva128->i2c.data <<= 1; + riva128->i2c.addr |= riva128->i2c.sda; + riva128->i2c.databits++; + if(riva128->i2c.databits == 8) + { + if(riva128->i2c.addr == 0xA0) + { + //pclog("RIVA 128 Write EDID Address %02x\n", riva128->i2c.data); + riva128->i2c.edid_rom.addr = riva128->i2c.data; + } + riva128->i2c.databits = 0; + } + } break; } //if(svga->crtcreg > 0x18) @@ -2226,14 +2333,14 @@ static void riva128_out(uint16_t addr, uint8_t val, void *p) svga_out(addr, val, svga); } -static uint32_t riva128_ramin_readl(uint32_t addr, void *p) + uint32_t riva128_ramin_readl(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint32_t ret = riva128->pramin[(addr & 0x1ffffc) >> 2]; return ret; } -static uint8_t riva128_ramin_readb(uint32_t addr, void *p) + uint8_t riva128_ramin_readb(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint32_t ret = riva128->pramin[(addr & 0x1ffffc) >> 2]; @@ -2241,7 +2348,7 @@ static uint8_t riva128_ramin_readb(uint32_t addr, void *p) return ret; } -static uint16_t riva128_ramin_readw(uint32_t addr, void *p) + uint16_t riva128_ramin_readw(uint32_t addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint32_t ret = riva128->pramin[(addr & 0x1ffffc) >> 2]; @@ -2249,13 +2356,13 @@ static uint16_t riva128_ramin_readw(uint32_t addr, void *p) return ret; } -static void riva128_ramin_writel(uint32_t addr, uint32_t val, void *p) + void riva128_ramin_writel(uint32_t addr, uint32_t val, void *p) { riva128_t *riva128 = (riva128_t *)p; riva128->pramin[(addr & 0x1ffffc) >> 2] = val; } -static void riva128_ramin_writeb(uint32_t addr, uint8_t val, void *p) + void riva128_ramin_writeb(uint32_t addr, uint8_t val, void *p) { uint32_t tmp = riva128_ramin_readl(addr,p); tmp &= ~(0xff << ((addr & 3) << 3)); @@ -2263,7 +2370,7 @@ static void riva128_ramin_writeb(uint32_t addr, uint8_t val, void *p) riva128_ramin_writel(addr, tmp, p); } -static void riva128_ramin_writew(uint32_t addr, uint16_t val, void *p) + void riva128_ramin_writew(uint32_t addr, uint16_t val, void *p) { uint32_t tmp = riva128_ramin_readl(addr,p); tmp &= ~(0xffff << ((addr & 2) << 4)); @@ -2271,7 +2378,7 @@ static void riva128_ramin_writew(uint32_t addr, uint16_t val, void *p) riva128_ramin_writel(addr, tmp, p); } -static uint8_t riva128_pci_read(int func, int addr, void *p) + uint8_t riva128_pci_read(int func, int addr, void *p) { riva128_t *riva128 = (riva128_t *)p; uint8_t ret = 0; @@ -2369,7 +2476,7 @@ static uint8_t riva128_pci_read(int func, int addr, void *p) return ret; } -static void riva128_reenable_svga_mappings(svga_t *svga) + void riva128_reenable_svga_mappings(svga_t *svga) { switch (svga->gdcreg[6] & 0xc) /*Banked framebuffer*/ { @@ -2392,7 +2499,7 @@ static void riva128_reenable_svga_mappings(svga_t *svga) } } -static void riva128_pci_write(int func, int addr, uint8_t val, void *p) + void riva128_pci_write(int func, int addr, uint8_t val, void *p) { //pclog("RIVA 128 PCI write %02X %02X %04X:%08X\n", addr, val, CS, cpu_state.pc); riva128_t *riva128 = (riva128_t *)p; @@ -2507,7 +2614,7 @@ static void riva128_pci_write(int func, int addr, uint8_t val, void *p) } } -static void rivatnt_pci_write(int func, int addr, uint8_t val, void *p) + void rivatnt_pci_write(int func, int addr, uint8_t val, void *p) { //pclog("RIVA 128 PCI write %02X %02X %04X:%08X\n", addr, val, CS, cpu_state.pc); riva128_t *riva128 = (riva128_t *)p; @@ -2618,7 +2725,7 @@ static void rivatnt_pci_write(int func, int addr, uint8_t val, void *p) } } -static void riva128_recalctimings(svga_t *svga) + void riva128_recalctimings(svga_t *svga) { riva128_t *riva128 = (riva128_t *)svga->p; @@ -2698,7 +2805,7 @@ static void riva128_recalctimings(svga_t *svga) riva128->nvfreq = freq; } -static void *riva128_init() + void *riva128_init() { riva128_t *riva128 = malloc(sizeof(riva128_t)); memset(riva128, 0, sizeof(riva128_t)); @@ -2770,15 +2877,13 @@ static void *riva128_init() riva128->pci_regs[0x32] = 0x0c; riva128->pci_regs[0x33] = 0x00; - riva128->pci_regs[0x3c] = device_get_config_int("irq"); - riva128->pmc.intr = 0; riva128->pbus.intr = 0; riva128->pfifo.intr = 0; riva128->pgraph.intr = 0; riva128->ptimer.intr = 0; - pci_add(riva128_pci_read, riva128_pci_write, riva128); + riva128->pci_card = pci_add(riva128_pci_read, riva128_pci_write, riva128); riva128->ptimer.clock_mul = 1; riva128->ptimer.clock_div = 1; @@ -2792,14 +2897,44 @@ static void *riva128_init() riva128->pramdac.nv_n = 0xc2; riva128->pramdac.nv_p = 0x0d; + riva128->i2c.addrbits = 0; + riva128->i2c.databits = 0; + riva128->i2c.busy = 0; + + uint8_t edid_rom[128] = {0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, + 0x04, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x05, 0x08, 0x01, 0x03, 0x81, 0x32, 0x26, 0x78, + 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x21, 0x08, 0x00, 0x61, 0x40, + 0x45, 0x40, 0x31, 0x40, 0x01, 0x01, 0x01, 0x01, + 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x00, 0x00, + 0x00, 0xfd, 0x00, 0x01, 0xff, 0x01, 0xff, 0xff, + 0x00, 0x0a, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xec}; + + { + int i = 0; + for(;i<128;i++) + { + riva128->i2c.edid_rom.edid_rom[i] = edid_rom[i]; + } + } + timer_add(riva128_mclk_poll, &riva128->mtime, TIMER_ALWAYS_ENABLED, riva128); timer_add(riva128_nvclk_poll, &riva128->nvtime, TIMER_ALWAYS_ENABLED, riva128); - timer_add(riva128_vblank_poll, &riva128->svga.vidtime, TIMER_ALWAYS_ENABLED, riva128); + + riva128->svga.vblank_start = riva128_vblank_poll; return riva128; } -static void riva128_close(void *p) + void riva128_close(void *p) { riva128_t *riva128 = (riva128_t *)p; FILE *f = fopen("vram.dmp", "wb"); @@ -2811,33 +2946,33 @@ static void riva128_close(void *p) free(riva128); } -static int riva128_available() + int riva128_available() { return rom_present(L"roms/video/nv_riva128/Diamond_V330_rev-e.vbi"); } -static void riva128_speed_changed(void *p) + void riva128_speed_changed(void *p) { riva128_t *riva128 = (riva128_t *)p; svga_recalctimings(&riva128->svga); } -static void riva128_force_redraw(void *p) +void riva128_force_redraw(void *p) { riva128_t *riva128 = (riva128_t *)p; riva128->svga.fullchange = changeframecount; } -static void riva128_add_status_info(char *s, int max_len, void *p) +void riva128_add_status_info(char *s, int max_len, void *p) { riva128_t *riva128 = (riva128_t *)p; svga_add_status_info(s, max_len, &riva128->svga); } -static device_config_t riva128_config[] = +device_config_t riva128_config[] = { { "memory", "Memory size", CONFIG_SELECTION, "", 4, @@ -2857,49 +2992,11 @@ static device_config_t riva128_config[] = }, }, { - "irq", "IRQ", CONFIG_SELECTION, "", 3, - { - { - "IRQ 3", 3 - }, - { - "IRQ 4", 4 - }, - { - "IRQ 5", 5 - }, - { - "IRQ 7", 7 - }, - { - "IRQ 9", 9 - }, - { - "IRQ 10", 10 - }, - { - "IRQ 11", 11 - }, - { - "IRQ 12", 12 - }, - { - "IRQ 14", 14 - }, - { - "IRQ 15", 15 - }, - { - "" - } - }, - }, - { - -1 + "", "", -1 } }; -/*static device_config_t riva128zx_config[] = +/* device_config_t riva128zx_config[] = { { .name = "memory", @@ -2929,58 +3026,6 @@ static device_config_t riva128_config[] = }, .default_int = 4 }, - { - .name = "irq", - .description = "IRQ", - .type = CONFIG_SELECTION, - .selection = - { - { - .description = "IRQ 3", - .value = 3 - }, - { - .description = "IRQ 4", - .value = 4 - }, - { - .description = "IRQ 5", - .value = 5 - }, - { - .description = "IRQ 7", - .value = 7 - }, - { - .description = "IRQ 9", - .value = 9 - }, - { - .description = "IRQ 10", - .value = 10 - }, - { - .description = "IRQ 11", - .value = 11 - }, - { - .description = "IRQ 12", - .value = 12 - }, - { - .description = "IRQ 14", - .value = 14 - }, - { - .description = "IRQ 15", - .value = 15 - }, - { - .description = "" - } - }, - .default_int = 3 - }, { .type = -1 } @@ -2999,7 +3044,7 @@ device_t riva128_device = riva128_config }; -static void *rivatnt_init() + void *rivatnt_init() { riva128_t *riva128 = malloc(sizeof(riva128_t)); memset(riva128, 0, sizeof(riva128_t)); @@ -3059,14 +3104,12 @@ static void *rivatnt_init() riva128->pci_regs[0x32] = 0x0c; riva128->pci_regs[0x33] = 0x00; - riva128->pci_regs[0x3c] = device_get_config_int("irq"); - riva128->pmc.intr = 0; riva128->pbus.intr = 0; riva128->pfifo.intr = 0; riva128->pgraph.intr = 0; - pci_add(riva128_pci_read, rivatnt_pci_write, riva128); + riva128->pci_card = pci_add(riva128_pci_read, rivatnt_pci_write, riva128); //Some bullshit default values so that the emulator won't shit itself trying to boot. These'll be overwritten by the video BIOS anyway. riva128->pramdac.m_m = 0x03; @@ -3077,14 +3120,44 @@ static void *rivatnt_init() riva128->pramdac.nv_n = 0xc2; riva128->pramdac.nv_p = 0x0d; + riva128->i2c.addrbits = 0; + riva128->i2c.databits = 0; + riva128->i2c.busy = 0; + + uint8_t edid_rom[128] = {0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, + 0x04, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x05, 0x08, 0x01, 0x03, 0x81, 0x32, 0x26, 0x78, + 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x21, 0x08, 0x00, 0x61, 0x40, + 0x45, 0x40, 0x31, 0x40, 0x01, 0x01, 0x01, 0x01, + 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x00, 0x00, + 0x00, 0xfd, 0x00, 0x01, 0xff, 0x01, 0xff, 0xff, + 0x00, 0x0a, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xec}; + + { + int i = 0; + for(;i<128;i++) + { + riva128->i2c.edid_rom.edid_rom[i] = edid_rom[i]; + } + } + timer_add(riva128_mclk_poll, &riva128->mtime, TIMER_ALWAYS_ENABLED, riva128); timer_add(riva128_nvclk_poll, &riva128->nvtime, TIMER_ALWAYS_ENABLED, riva128); - timer_add(riva128_vblank_poll, &riva128->svga.vidtime, TIMER_ALWAYS_ENABLED, riva128); + + riva128->svga.vblank_start = riva128_vblank_poll; return riva128; } -static void rivatnt_close(void *p) + void rivatnt_close(void *p) { riva128_t *riva128 = (riva128_t *)p; FILE *f = fopen("vram.dmp", "wb"); @@ -3096,33 +3169,33 @@ static void rivatnt_close(void *p) free(riva128); } -static int rivatnt_available() + int rivatnt_available() { return rom_present(L"roms/video/nv_riva128/NV4_diamond_revB.rom"); } -static void rivatnt_speed_changed(void *p) + void rivatnt_speed_changed(void *p) { riva128_t *riva128 = (riva128_t *)p; svga_recalctimings(&riva128->svga); } -static void rivatnt_force_redraw(void *p) + void rivatnt_force_redraw(void *p) { riva128_t *riva128 = (riva128_t *)p; riva128->svga.fullchange = changeframecount; } -static void rivatnt_add_status_info(char *s, int max_len, void *p) + void rivatnt_add_status_info(char *s, int max_len, void *p) { riva128_t *riva128 = (riva128_t *)p; svga_add_status_info(s, max_len, &riva128->svga); } -static device_config_t rivatnt_config[] = + device_config_t rivatnt_config[] = { { "memory", "Memory size", CONFIG_SELECTION, "", 16, @@ -3142,45 +3215,7 @@ static device_config_t rivatnt_config[] = }, }, { - "irq", "IRQ", CONFIG_SELECTION, "", 3, - { - { - "IRQ 3", 3 - }, - { - "IRQ 4", 4 - }, - { - "IRQ 5", 5 - }, - { - "IRQ 7", 7 - }, - { - "IRQ 9", 9 - }, - { - "IRQ 10", 10 - }, - { - "IRQ 11", 11 - }, - { - "IRQ 12", 12 - }, - { - "IRQ 14", 14 - }, - { - "IRQ 15", 15 - }, - { - "" - } - }, - }, - { - -1 + "", "", -1 } }; @@ -3197,7 +3232,7 @@ device_t rivatnt_device = rivatnt_config }; -static void *rivatnt2_init() + void *rivatnt2_init() { riva128_t *riva128 = malloc(sizeof(riva128_t)); memset(riva128, 0, sizeof(riva128_t)); @@ -3270,14 +3305,12 @@ static void *rivatnt2_init() riva128->pci_regs[0x32] = 0x0c; riva128->pci_regs[0x33] = 0x00; - riva128->pci_regs[0x3c] = device_get_config_int("irq"); - riva128->pmc.intr = 0; riva128->pbus.intr = 0; riva128->pfifo.intr = 0; riva128->pgraph.intr = 0; - pci_add(riva128_pci_read, rivatnt_pci_write, riva128); + riva128->pci_card = pci_add(riva128_pci_read, rivatnt_pci_write, riva128); //Some bullshit default values so that the emulator won't shit itself trying to boot. These'll be overwritten by the video BIOS anyway. riva128->pramdac.m_m = 0x03; @@ -3288,14 +3321,44 @@ static void *rivatnt2_init() riva128->pramdac.nv_n = 0xc2; riva128->pramdac.nv_p = 0x0d; + riva128->i2c.addrbits = 0; + riva128->i2c.databits = 0; + riva128->i2c.busy = 0; + + uint8_t edid_rom[128] = {0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, + 0x04, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x05, 0x08, 0x01, 0x03, 0x81, 0x32, 0x26, 0x78, + 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x21, 0x08, 0x00, 0x61, 0x40, + 0x45, 0x40, 0x31, 0x40, 0x01, 0x01, 0x01, 0x01, + 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x00, 0x00, + 0x00, 0xfd, 0x00, 0x01, 0xff, 0x01, 0xff, 0xff, + 0x00, 0x0a, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xec}; + + { + int i = 0; + for(;i<128;i++) + { + riva128->i2c.edid_rom.edid_rom[i] = edid_rom[i]; + } + } + timer_add(riva128_mclk_poll, &riva128->mtime, TIMER_ALWAYS_ENABLED, riva128); timer_add(riva128_nvclk_poll, &riva128->nvtime, TIMER_ALWAYS_ENABLED, riva128); - timer_add(riva128_vblank_poll, &riva128->svga.vidtime, TIMER_ALWAYS_ENABLED, riva128); + + riva128->svga.vblank_start = riva128_vblank_poll; return riva128; } -static void rivatnt2_close(void *p) + void rivatnt2_close(void *p) { riva128_t *riva128 = (riva128_t *)p; FILE *f = fopen("vram.dmp", "wb"); @@ -3307,33 +3370,33 @@ static void rivatnt2_close(void *p) free(riva128); } -static int rivatnt2_available() + int rivatnt2_available() { return rom_present(L"roms/video/nv_riva128/NV5diamond.bin") || rom_present(L"roms/video/nv_riva128/inno3d64bit.BIN") || rom_present(L"roms/video/nv_riva128/creative.BIN"); } -static void rivatnt2_speed_changed(void *p) + void rivatnt2_speed_changed(void *p) { riva128_t *riva128 = (riva128_t *)p; svga_recalctimings(&riva128->svga); } -static void rivatnt2_force_redraw(void *p) + void rivatnt2_force_redraw(void *p) { riva128_t *riva128 = (riva128_t *)p; riva128->svga.fullchange = changeframecount; } -static void rivatnt2_add_status_info(char *s, int max_len, void *p) + void rivatnt2_add_status_info(char *s, int max_len, void *p) { riva128_t *riva128 = (riva128_t *)p; svga_add_status_info(s, max_len, &riva128->svga); } -static device_config_t rivatnt2_config[] = + device_config_t rivatnt2_config[] = { { "model", "Card model", CONFIG_SELECTION, "", 0, @@ -3369,44 +3432,6 @@ static device_config_t rivatnt2_config[] = } }, }, - { - "irq", "IRQ", CONFIG_SELECTION, "", 3, - { - { - "IRQ 3", 3 - }, - { - "IRQ 4", 4 - }, - { - "IRQ 5", 5 - }, - { - "IRQ 7", 7 - }, - { - "IRQ 9", 9 - }, - { - "IRQ 10", 10 - }, - { - "IRQ 11", 11 - }, - { - "IRQ 12", 12 - }, - { - "IRQ 14", 14 - }, - { - "IRQ 15", 15 - }, - { - "" - } - }, - }, { "", "", -1 } @@ -3424,4 +3449,3 @@ device_t rivatnt2_device = rivatnt2_add_status_info, rivatnt2_config }; - diff --git a/src/VIDEO/video.c b/src/VIDEO/video.c index 5a7d2dc78..9e0d801f8 100644 --- a/src/VIDEO/video.c +++ b/src/VIDEO/video.c @@ -93,6 +93,10 @@ static VIDEO_CARD video_cards[] = {"MDA", "mda", &mda_device, GFX_MDA}, {"MDSI Genius", "genius", &genius_device, GFX_GENIUS}, {"Number Nine 9FX (S3 Trio64)", "n9_9fx", &s3_9fx_device, GFX_N9_9FX}, +#ifdef DEV_BRANCH + {"nVidia RIVA 128", "riva128", &riva128_device, GFX_RIVA128}, + {"nVidia RIVA TNT", "rivatnt", &rivatnt_device, GFX_RIVATNT}, +#endif {"OAK OTI-067", "oti067", &oti067_device, GFX_OTI067}, {"OAK OTI-077", "oti077", &oti077_device, GFX_OTI077}, {"Paradise Bahamas 64 (S3 Vision864)", "bahamas64", &s3_bahamas64_device, GFX_BAHAMAS64},