trunk/src/mame/drivers/twinkle.c
| r242964 | r242965 | |
| 254 | 254 | m_maincpu(*this, "maincpu"), |
| 255 | 255 | m_audiocpu(*this, "audiocpu") |
| 256 | 256 | { |
| 257 | | m_spu_hle[0x200] = 0; |
| 258 | | m_spu_hle[0x202] = 0; |
| 259 | 257 | } |
| 260 | 258 | |
| 261 | 259 | required_device<am53cf96_device> m_am53cf96; |
| r242964 | r242965 | |
| 264 | 262 | |
| 265 | 263 | UINT16 m_spu_ctrl; // SPU board control register |
| 266 | 264 | UINT8 m_spu_shared[0x400]; // SPU/PSX shared dual-ported RAM |
| 267 | | UINT8 m_spu_hle[0x400]; |
| 268 | 265 | UINT32 m_spu_ata_dma; |
| 269 | 266 | int m_spu_ata_dmarq; |
| 270 | 267 | |
| r242964 | r242965 | |
| 285 | 282 | DECLARE_WRITE16_MEMBER(twinkle_waveram_w); |
| 286 | 283 | DECLARE_READ16_MEMBER(shared_68k_r); |
| 287 | 284 | DECLARE_WRITE16_MEMBER(shared_68k_w); |
| 285 | DECLARE_READ16_MEMBER(unk_68k_r); |
| 288 | 286 | DECLARE_WRITE_LINE_MEMBER(spu_ata_irq); |
| 289 | 287 | DECLARE_WRITE_LINE_MEMBER(spu_ata_dmarq); |
| 290 | 288 | required_device<cpu_device> m_maincpu; |
| r242964 | r242965 | |
| 671 | 669 | |
| 672 | 670 | WRITE8_MEMBER(twinkle_state::shared_psx_w) |
| 673 | 671 | { |
| 674 | | //printf("shared_psx_w: %04x, %04x, %04x\n", offset, data, mem_mask); |
| 672 | // printf("shared_psx_w: %04x, %04x, %04x\n", offset, data, mem_mask); |
| 675 | 673 | |
| 676 | 674 | m_spu_shared[offset] = data; |
| 677 | 675 | |
| 678 | | // HLE sound board |
| 679 | | m_spu_hle[offset] = data; |
| 680 | | |
| 681 | 676 | if (offset == 0x03fe && data == 0xff) |
| 682 | 677 | { |
| 683 | | //printf("spu command %02x %02x\n", m_spu_hle[1], m_spu_hle[3]); |
| 678 | // printf("spu command %02x %02x\n", m_spu_shared[1], m_spu_shared[3]); |
| 684 | 679 | |
| 685 | | for (int i = 0x200; i < 0x300; i++) m_spu_hle[i] = 0xea; |
| 686 | | |
| 687 | | switch (m_spu_hle[1]) |
| 688 | | { |
| 689 | | case 0x91: // hdd sum 1 |
| 690 | | m_spu_hle[0x200] = 0; // ? |
| 691 | | m_spu_hle[0x202] = 0; // ? |
| 692 | | break; |
| 693 | | |
| 694 | | case 0x9a: // hdd sum 2 |
| 695 | | m_spu_hle[0x200] = 0; // ? |
| 696 | | m_spu_hle[0x202] = 0; // ? |
| 697 | | m_spu_hle[0x203] = 1; // Must be 1 to pass test |
| 698 | | break; |
| 699 | | |
| 700 | | case 0xa1: // version |
| 701 | | m_spu_hle[0x200] = 0; // ? |
| 702 | | m_spu_hle[0x202] = 0; // ? |
| 703 | | |
| 704 | | if (strcmp(machine().system().name, "bmiidx") == 0 || |
| 705 | | strcmp(machine().system().name, "bmiidxa") == 0 || |
| 706 | | strcmp(machine().system().name, "bmiidxc") == 0 || |
| 707 | | strcmp(machine().system().name, "bmiidxca") == 0) |
| 708 | | { |
| 709 | | strcpy((char *)&m_spu_hle[0x204], "GQ863JA_A"); |
| 710 | | } |
| 711 | | else if (strcmp(machine().system().name, "bmiidxs") == 0 || |
| 712 | | strcmp(machine().system().name, "bmiidxc2") == 0) |
| 713 | | { |
| 714 | | strcpy((char *)&m_spu_hle[0x204], "GC983JA_R"); |
| 715 | | } |
| 716 | | else if (strcmp(machine().system().name, "bmiidx2") == 0) |
| 717 | | { |
| 718 | | strcpy((char *)&m_spu_hle[0x204], "GC985JA_A"); |
| 719 | | } |
| 720 | | else if (strcmp(machine().system().name, "bmiidx3") == 0 || |
| 721 | | strcmp(machine().system().name, "bmiidx3a") == 0) |
| 722 | | { |
| 723 | | strcpy((char *)&m_spu_hle[0x204], "GC992JA_A"); |
| 724 | | } |
| 725 | | else if (strcmp(machine().system().name, "bmiidx4") == 0) |
| 726 | | { |
| 727 | | strcpy((char *)&m_spu_hle[0x204], "GCA03JA_A"); |
| 728 | | } |
| 729 | | else if (strcmp(machine().system().name, "bmiidx5") == 0) |
| 730 | | { |
| 731 | | strcpy((char *)&m_spu_hle[0x204], "GCA17JA_A"); |
| 732 | | } |
| 733 | | else if (strcmp(machine().system().name, "bmiidx6") == 0 || |
| 734 | | strcmp(machine().system().name, "bmiidx6a") == 0) |
| 735 | | { |
| 736 | | strcpy((char *)&m_spu_hle[0x204], "GCB4UJA_A"); |
| 737 | | } |
| 738 | | else if (strcmp(machine().system().name, "bmiidx7") == 0) |
| 739 | | { |
| 740 | | strcpy((char *)&m_spu_hle[0x204], "GCB44JA_A"); |
| 741 | | } |
| 742 | | else if (strcmp(machine().system().name, "bmiidx8") == 0) |
| 743 | | { |
| 744 | | strcpy((char *)&m_spu_hle[0x204], "GCC44JA_A"); |
| 745 | | } |
| 746 | | break; |
| 747 | | |
| 748 | | case 0x30: // play sound [3]=sound code |
| 749 | | case 0x51: // sound off |
| 750 | | case 0x25: // spu rom error ([3]==0x0f) |
| 751 | | case 0x26: // spu rom error ([3]==0x0f) |
| 752 | | case 0x08: // spu rom error |
| 753 | | case 0x40: // spu rom error ([3]==0x01 coin sound?) |
| 754 | | case 0x2f: // spu rom error |
| 755 | | case 0x52: // spu rom error |
| 756 | | case 0x04: // spu rom error ([3]==?) |
| 757 | | m_spu_hle[0x200] = 0; |
| 758 | | m_spu_hle[0x202] = 0; |
| 759 | | break; |
| 760 | | } |
| 680 | m_audiocpu->set_input_line(M68K_IRQ_4, HOLD_LINE); |
| 761 | 681 | } |
| 762 | 682 | } |
| 763 | 683 | |
| 764 | 684 | READ8_MEMBER(twinkle_state::shared_psx_r) |
| 765 | 685 | { |
| 766 | | //UINT32 result = m_spu_shared[offset]; |
| 767 | | UINT32 result = m_spu_hle[offset]; |
| 686 | UINT32 result = m_spu_shared[offset]; |
| 768 | 687 | |
| 769 | 688 | //printf("shared_psx_r: %04x, %04x, %04x\n", offset, result, mem_mask); |
| 770 | 689 | |
| r242964 | r242965 | |
| 803 | 722 | /* |
| 804 | 723 | System control register (Konami always has one) |
| 805 | 724 | |
| 806 | | bit 7 = write 0 to ack IRQ 1, write 1 to enable (IRQ 1 appears to be vblank) |
| 725 | bit 7 = write 0 to ack IRQ 1, write 1 to enable (IRQ 1 appears to be an RF5C400-related timer, or some free-running timing source) |
| 807 | 726 | bit 8 = write 0 to ack IRQ 2, write 1 to enable (IRQ 2 appears to be DMA completion) |
| 808 | | bit 9 = write 0 to ack IRQ 4, write 1 to enable (IRQ 4 appears to be "command sent", unsure how the MIPS causes it yet however) |
| 809 | | bit 10 = write 0 to ack IRQ 6, write 1 to enable (IRQ 6 is IDE) |
| 810 | | bit 11 = watchdog toggle? |
| 727 | bit 9 = write 0 to ack IRQ 4, write 1 to enable (IRQ 4 is "command available") |
| 728 | bit 10 = write 0 to ack IRQ 6, write 1 to enable (IRQ 6 is the ATA IRQ) |
| 729 | bit 11 = watchdog toggle |
| 811 | 730 | |
| 812 | 731 | Other bits unknown. |
| 813 | 732 | */ |
| r242964 | r242965 | |
| 836 | 755 | WRITE16_MEMBER(twinkle_state::spu_ata_dma_low_w) |
| 837 | 756 | { |
| 838 | 757 | m_spu_ata_dma = (m_spu_ata_dma & ~0xffff) | data; |
| 839 | | |
| 840 | | //printf("dma_low %08x\n", m_spu_ata_dma * 2); |
| 841 | 758 | } |
| 842 | 759 | |
| 843 | 760 | WRITE16_MEMBER(twinkle_state::spu_ata_dma_high_w) |
| 844 | 761 | { |
| 845 | 762 | m_spu_ata_dma = (m_spu_ata_dma & 0xffff) | (data << 16); |
| 846 | | |
| 847 | | //printf("dma_high %08x\n", m_spu_ata_dma * 2); |
| 848 | 763 | } |
| 849 | 764 | |
| 850 | 765 | WRITE_LINE_MEMBER(twinkle_state::spu_ata_dmarq) |
| r242964 | r242965 | |
| 864 | 779 | //waveram[m_spu_ata_dma++] = (data >> 8) | (data << 8); |
| 865 | 780 | // bp 4a0e ;bmiidx4 checksum |
| 866 | 781 | // bp 4d62 ;bmiidx4 dma |
| 867 | | m_waveram[m_spu_ata_dma++] = data; |
| 782 | |
| 783 | // $$$HACK - game DMAs nothing useful to 0x400000 but all sound plays are 0x400000 or above |
| 784 | // so limit sound RAM to 4MB (there's 6 MB on the board) and let the 5c400's address masking |
| 785 | // work for us until we figure out what's actually going on. |
| 786 | if (m_spu_ata_dma < 0x200000) |
| 787 | { |
| 788 | m_waveram[m_spu_ata_dma++] = data; |
| 789 | } |
| 868 | 790 | } |
| 869 | 791 | |
| 870 | 792 | m_ata->write_dmack(CLEAR_LINE); |
| r242964 | r242965 | |
| 886 | 808 | { |
| 887 | 809 | UINT16 result = m_spu_shared[offset]; |
| 888 | 810 | |
| 889 | | //printf("shared_68k_r: %04x, %04x, %04x\n", offset, result, mem_mask); |
| 811 | // printf("shared_68k_r: %04x, %04x, %04x\n", offset, result, mem_mask); |
| 890 | 812 | |
| 891 | 813 | return result; |
| 892 | 814 | } |
| 893 | 815 | |
| 894 | 816 | WRITE16_MEMBER(twinkle_state::shared_68k_w) |
| 895 | 817 | { |
| 896 | | //printf("shared_68k_w: %04x, %04x, %04x\n", offset, data, mem_mask); |
| 818 | // printf("shared_68k_w: %04x, %04x, %04x\n", offset, data, mem_mask); |
| 897 | 819 | |
| 898 | 820 | m_spu_shared[offset] = data & 0xff; |
| 899 | 821 | } |
| 900 | 822 | |
| 823 | READ16_MEMBER(twinkle_state::unk_68k_r) |
| 824 | { |
| 825 | return 0xffff; // must return 0xff for 68000 POST to complete properly |
| 826 | } |
| 827 | |
| 901 | 828 | static ADDRESS_MAP_START( sound_map, AS_PROGRAM, 16, twinkle_state ) |
| 902 | 829 | AM_RANGE(0x000000, 0x07ffff) AM_ROM |
| 903 | 830 | AM_RANGE(0x100000, 0x13ffff) AM_RAM |
| 831 | AM_RANGE(0x200000, 0x200001) AM_READ(unk_68k_r) |
| 904 | 832 | // 220000 = LEDs? |
| 905 | 833 | AM_RANGE(0x230000, 0x230003) AM_WRITE(twinkle_spu_ctrl_w) |
| 906 | 834 | AM_RANGE(0x240000, 0x240003) AM_WRITE(spu_ata_dma_low_w) |
| r242964 | r242965 | |
| 909 | 837 | AM_RANGE(0x280000, 0x280fff) AM_READWRITE(shared_68k_r, shared_68k_w) |
| 910 | 838 | AM_RANGE(0x300000, 0x30000f) AM_DEVREADWRITE("ata", ata_interface_device, read_cs0, write_cs0) |
| 911 | 839 | // 34000E = ??? |
| 840 | AM_RANGE(0x34000e, 0x34000f) AM_WRITENOP |
| 912 | 841 | AM_RANGE(0x400000, 0x400fff) AM_DEVREADWRITE("rfsnd", rf5c400_device, rf5c400_r, rf5c400_w) |
| 913 | | AM_RANGE(0x800000, 0xffffff) AM_READWRITE(twinkle_waveram_r, twinkle_waveram_w ) // 8 MB window wave RAM |
| 842 | AM_RANGE(0x800000, 0xbfffff) AM_READWRITE(twinkle_waveram_r, twinkle_waveram_w ) |
| 843 | AM_RANGE(0xfe0000, 0xffffff) AM_RAM // ...and the RAM test checks this last 128k (mirror of the work RAM at 0x100000?) |
| 914 | 844 | ADDRESS_MAP_END |
| 915 | 845 | |
| 916 | 846 | /* SCSI */ |
| r242964 | r242965 | |
| 1011 | 941 | |
| 1012 | 942 | MCFG_CPU_ADD("audiocpu", M68000, 32000000/2) /* 16.000 MHz */ |
| 1013 | 943 | MCFG_CPU_PROGRAM_MAP( sound_map ) |
| 944 | MCFG_CPU_PERIODIC_INT_DRIVER(twinkle_state, irq1_line_assert, 60) |
| 945 | MCFG_CPU_PERIODIC_INT_DRIVER(twinkle_state, irq2_line_assert, 60) |
| 1014 | 946 | |
| 1015 | 947 | MCFG_WATCHDOG_TIME_INIT(attotime::from_msec(1200)) /* check TD pin on LTC1232 */ |
| 1016 | 948 | |
| r242964 | r242965 | |
| 1149 | 1081 | ROM_REGION32_LE( 0x080000, "audiocpu", 0 )\ |
| 1150 | 1082 | ROM_LOAD16_WORD_SWAP( "863a05.2x", 0x000000, 0x080000, CRC(6f42a09e) SHA1(cab5209f90f47b9ee6e721479913ad74e3ba84b1) )\ |
| 1151 | 1083 | \ |
| 1152 | | ROM_REGION16_LE(0x1800000, "rfsnd", ROMREGION_ERASE00) |
| 1084 | ROM_REGION16_LE(0x400000, "rfsnd", ROMREGION_ERASE00) |
| 1153 | 1085 | |
| 1154 | 1086 | ROM_START( gq863 ) |
| 1155 | 1087 | TWINKLE_BIOS |