diff options
| author | 2013-10-14 00:16:11 +0000 | |
|---|---|---|
| committer | 2013-10-14 00:16:11 +0000 | |
| commit | e1ad28991619464ec8d1652e80245c609d686dfb (patch) | |
| tree | e0b4b1ad95bc88d35bee74350145898a846a9ac7 | |
| parent | d24837538af4cdaaa8a3408c83e547fa48ab2db7 (diff) | |
shunt some IGS code around (nw)
| -rw-r--r-- | .gitattributes | 2 | ||||
| -rw-r--r-- | src/mame/includes/pgm.h | 14 | ||||
| -rw-r--r-- | src/mame/machine/igs028.c | 204 | ||||
| -rw-r--r-- | src/mame/machine/igs028.h | 28 | ||||
| -rw-r--r-- | src/mame/machine/pgmprot_igs025_igs028.c | 150 | ||||
| -rw-r--r-- | src/mame/mame.mak | 1 |
6 files changed, 248 insertions, 151 deletions
diff --git a/.gitattributes b/.gitattributes index 3725a9c7789..3f46db7e009 100644 --- a/.gitattributes +++ b/.gitattributes @@ -5107,6 +5107,8 @@ src/mame/machine/igs022.c svneol=native#text/plain src/mame/machine/igs022.h svneol=native#text/plain src/mame/machine/igs025.c svneol=native#text/plain src/mame/machine/igs025.h svneol=native#text/plain +src/mame/machine/igs028.c svneol=native#text/plain +src/mame/machine/igs028.h svneol=native#text/plain src/mame/machine/irem_cpu.c svneol=native#text/plain src/mame/machine/irem_cpu.h svneol=native#text/plain src/mame/machine/irobot.c svneol=native#text/plain diff --git a/src/mame/includes/pgm.h b/src/mame/includes/pgm.h index bf3df4b59cc..c9373c743a3 100644 --- a/src/mame/includes/pgm.h +++ b/src/mame/includes/pgm.h @@ -10,6 +10,7 @@ #include "machine/igs025.h" #include "machine/igs022.h" +#include "machine/igs028.h" #define PGMARM7LOGERROR 0 @@ -449,7 +450,10 @@ class pgm_028_025_state : public pgm_state public: pgm_028_025_state(const machine_config &mconfig, device_type type, const char *tag) : pgm_state(mconfig, type, tag), - m_sharedprotram(*this, "sharedprotram") { + m_sharedprotram(*this, "sharedprotram"), + m_igs028(*this,"igs028") + + { } int m_olds_cmd; @@ -461,18 +465,16 @@ public: UINT16 m_olds_prot_hilo; UINT16 m_olds_prot_hilo_select; const UINT8 *m_olds_prot_hilo_source2; + required_shared_ptr<UINT16> m_sharedprotram; + required_device<igs028_device> m_igs028; DECLARE_DRIVER_INIT(olds); DECLARE_MACHINE_RESET(olds); - UINT32 olds_prot_addr( UINT16 addr ); - UINT32 olds_read_reg( UINT16 addr ); - void olds_write_reg( UINT16 addr, UINT32 val ); DECLARE_READ16_MEMBER( olds_r ); DECLARE_WRITE16_MEMBER( olds_w ); - DECLARE_READ16_MEMBER( olds_prot_swap_r ); - void IGS028_do_dma(UINT16 src, UINT16 dst, UINT16 size, UINT16 mode); + void olds_protection_calculate_hilo(); void olds_protection_calculate_hold(int y, int z); }; diff --git a/src/mame/machine/igs028.c b/src/mame/machine/igs028.c new file mode 100644 index 00000000000..1969be7a8b3 --- /dev/null +++ b/src/mame/machine/igs028.c @@ -0,0 +1,204 @@ +/* IGS 028 */ + +// this seems to be very similar to the igs022 - encrypted DMA + some other ops with shared RAM +// used by +// Oriental Legend Super / Special + + +#include "emu.h" +#include "igs028.h" + + +igs028_device::igs028_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) + : device_t(mconfig, IGS028, "IGS028", tag, owner, clock, "igs028", __FILE__) +{ +} + +void igs028_device::device_config_complete() +{ +} + +void igs028_device::device_validity_check(validity_checker &valid) const +{ +} + +void igs028_device::device_start() +{ + + m_sharedprotram = 0; + + +} + +void igs028_device::device_reset() +{ + + //printf("igs028_device::device_reset()"); + + + if (!m_sharedprotram) + { + logerror("m_sharedprotram was not set\n"); + return; + } + +// written by protection device +// there seems to be an auto-dma that writes from $401000-402573? + m_sharedprotram[0x1000/2] = 0x4749; // 'IGS.28' + m_sharedprotram[0x1002/2] = 0x2E53; + m_sharedprotram[0x1004/2] = 0x3832; + + m_sharedprotram[0x3064/2] = 0xB315; // crc? + +} + + +UINT32 igs028_device::olds_prot_addr(UINT16 addr) +{ + switch (addr & 0xff) + { + case 0x0: + case 0x5: + case 0xa: return 0x402a00 + ((addr >> 8) << 2); + case 0x2: + case 0x8: return 0x402e00 + ((addr >> 8) << 2); + case 0x1: return 0x40307e; + case 0x3: return 0x403090; + case 0x4: return 0x40309a; + case 0x6: return 0x4030a4; + case 0x7: return 0x403000; + case 0x9: return 0x40306e; + } + + return 0; +} + +UINT32 igs028_device::olds_read_reg(UINT16 addr) +{ + UINT32 protaddr = (olds_prot_addr(addr) - 0x400000) / 2; + return m_sharedprotram[protaddr] << 16 | m_sharedprotram[protaddr + 1]; +} + +void igs028_device::olds_write_reg( UINT16 addr, UINT32 val ) +{ + m_sharedprotram[((olds_prot_addr(addr) - 0x400000) / 2) + 0] = val >> 16; + m_sharedprotram[((olds_prot_addr(addr) - 0x400000) / 2) + 1] = val & 0xffff; +} + +void igs028_device::IGS028_do_dma(UINT16 src, UINT16 dst, UINT16 size, UINT16 mode) +{ + UINT16 param = mode >> 8; + UINT16 *PROTROM = (UINT16*)memregion(":user1")->base(); + +// logerror ("mode: %2.2x, src: %4.4x, dst: %4.4x, size: %4.4x, data: %4.4x\n", (mode &0xf), src, dst, size, mode); + + mode &= 0x0f; + + switch (mode) + { + case 0x00: // This mode copies code later on in the game! Encrypted somehow? + // src:2fc8, dst: 045a, size: 025e, mode: 0000 + // jumps from 12beb4 in unprotected set + // jumps from 1313e0 in protected set + case 0x01: // swap bytes and nibbles + case 0x02: // ^= encryption + case 0x05: // copy + case 0x06: // += encryption (correct?) + { + UINT8 extraoffset = param & 0xff; + UINT8 *dectable = (UINT8 *)(PROTROM + (0x100 / 2)); + + for (INT32 x = 0; x < size; x++) + { + UINT16 dat2 = PROTROM[src + x]; + + int taboff = ((x*2)+extraoffset) & 0xff; // must allow for overflow in instances of odd offsets + unsigned short extraxor = ((dectable[taboff + 0]) << 0) | (dectable[taboff + 1] << 8); + + if (mode==0) dat2 = 0x4e75; // hack + if (mode==1) dat2 = ((dat2 & 0xf000) >> 12) | ((dat2 & 0x0f00) >> 4) | ((dat2 & 0x00f0) << 4) | ((dat2 & 0x000f) << 12); + if (mode==2) dat2 ^= extraxor; + // if (mode==5) dat2 = dat2; + if (mode==6) dat2 += extraxor; + + if (mode==2 || mode==6) dat2 = (dat2<<8)|(dat2>>8); + + m_sharedprotram[dst + x] = (dat2 << 8) | (dat2 >> 8); + } + } + break; + + // default: + // logerror ("DMA mode unknown!!!\nsrc:%4.4x, dst: %4.4x, size: %4.4x, mode: %4.4x\n", src, dst, size, mode); + } +} + +void igs028_device::IGS028_handle() +{ + + UINT16 cmd = m_sharedprotram[0x3026 / 2]; + + // logerror ("command: %x\n", cmd); + + switch (cmd) + { + case 0x12: + { + UINT16 mode = m_sharedprotram[0x303e / 2]; // ? + UINT16 src = m_sharedprotram[0x306a / 2] >> 1; // ? + UINT16 dst = m_sharedprotram[0x3084 / 2] & 0x1fff; + UINT16 size = m_sharedprotram[0x30a2 / 2] & 0x1fff; + + IGS028_do_dma(src, dst, size, mode); + } + break; + + case 0x64: // incomplete? + { + UINT16 p1 = m_sharedprotram[0x3050 / 2]; + UINT16 p2 = m_sharedprotram[0x3082 / 2]; + UINT16 p3 = m_sharedprotram[0x3054 / 2]; + UINT16 p4 = m_sharedprotram[0x3088 / 2]; + + if (p2 == 0x02) + olds_write_reg(p1, olds_read_reg(p1) + 0x10000); + + switch (p4) + { + case 0xd: + olds_write_reg(p1,olds_read_reg(p3)); + break; + case 0x0: + olds_write_reg(p3,(olds_read_reg(p2))^(olds_read_reg(p1))); + break; + case 0xe: + olds_write_reg(p3,olds_read_reg(p3)+0x10000); + break; + case 0x2: + olds_write_reg(p1,(olds_read_reg(p2))+(olds_read_reg(p3))); + break; + case 0x6: + olds_write_reg(p3,(olds_read_reg(p2))&(olds_read_reg(p1))); + break; + case 0x1: + olds_write_reg(p2,olds_read_reg(p1)+0x10000); + break; + case 0x7: + olds_write_reg(p3,olds_read_reg(p1)); + break; + default: + break; + } + } + break; + + // default: + // logerror ("unemulated command!\n"); + } +} + + +const device_type IGS028 = &device_creator<igs028_device>; + + + diff --git a/src/mame/machine/igs028.h b/src/mame/machine/igs028.h new file mode 100644 index 00000000000..68dc1ce88ec --- /dev/null +++ b/src/mame/machine/igs028.h @@ -0,0 +1,28 @@ +/* IGS 028 */ + + + +class igs028_device : public device_t +{ +public: + igs028_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); + + UINT16* m_sharedprotram; + + void IGS028_handle(void); + +protected: + virtual void device_config_complete(); + virtual void device_validity_check(validity_checker &valid) const; + virtual void device_start(); + virtual void device_reset(); + + UINT32 olds_prot_addr(UINT16 addr); + UINT32 olds_read_reg(UINT16 addr); + void olds_write_reg( UINT16 addr, UINT32 val ); + void IGS028_do_dma(UINT16 src, UINT16 dst, UINT16 size, UINT16 mode); +}; + + + +extern const device_type IGS028; diff --git a/src/mame/machine/pgmprot_igs025_igs028.c b/src/mame/machine/pgmprot_igs025_igs028.c index 67489f761b2..069010d4479 100644 --- a/src/mame/machine/pgmprot_igs025_igs028.c +++ b/src/mame/machine/pgmprot_igs025_igs028.c @@ -149,86 +149,6 @@ static const UINT8 olds_source_data[8][0xec] = // table addresses $2951CA } }; -UINT32 pgm_028_025_state::olds_prot_addr(UINT16 addr) -{ - switch (addr & 0xff) - { - case 0x0: - case 0x5: - case 0xa: return 0x402a00 + ((addr >> 8) << 2); - case 0x2: - case 0x8: return 0x402e00 + ((addr >> 8) << 2); - case 0x1: return 0x40307e; - case 0x3: return 0x403090; - case 0x4: return 0x40309a; - case 0x6: return 0x4030a4; - case 0x7: return 0x403000; - case 0x9: return 0x40306e; - } - - return 0; -} - -UINT32 pgm_028_025_state::olds_read_reg(UINT16 addr) -{ - UINT32 protaddr = (olds_prot_addr(addr) - 0x400000) / 2; - return m_sharedprotram[protaddr] << 16 | m_sharedprotram[protaddr + 1]; -} - -void pgm_028_025_state::olds_write_reg( UINT16 addr, UINT32 val ) -{ - m_sharedprotram[((olds_prot_addr(addr) - 0x400000) / 2) + 0] = val >> 16; - m_sharedprotram[((olds_prot_addr(addr) - 0x400000) / 2) + 1] = val & 0xffff; -} - -void pgm_028_025_state::IGS028_do_dma(UINT16 src, UINT16 dst, UINT16 size, UINT16 mode) -{ - UINT16 param = mode >> 8; - UINT16 *PROTROM = (UINT16*)memregion("user1")->base(); - -// logerror ("mode: %2.2x, src: %4.4x, dst: %4.4x, size: %4.4x, data: %4.4x\n", (mode &0xf), src, dst, size, mode); - - mode &= 0x0f; - - switch (mode) - { - case 0x00: // This mode copies code later on in the game! Encrypted somehow? - // src:2fc8, dst: 045a, size: 025e, mode: 0000 - // jumps from 12beb4 in unprotected set - // jumps from 1313e0 in protected set - case 0x01: // swap bytes and nibbles - case 0x02: // ^= encryption - case 0x05: // copy - case 0x06: // += encryption (correct?) - { - UINT8 extraoffset = param & 0xff; - UINT8 *dectable = (UINT8 *)(PROTROM + (0x100 / 2)); - - for (INT32 x = 0; x < size; x++) - { - UINT16 dat2 = PROTROM[src + x]; - - int taboff = ((x*2)+extraoffset) & 0xff; // must allow for overflow in instances of odd offsets - unsigned short extraxor = ((dectable[taboff + 0]) << 0) | (dectable[taboff + 1] << 8); - - if (mode==0) dat2 = 0x4e75; // hack - if (mode==1) dat2 = ((dat2 & 0xf000) >> 12) | ((dat2 & 0x0f00) >> 4) | ((dat2 & 0x00f0) << 4) | ((dat2 & 0x000f) << 12); - if (mode==2) dat2 ^= extraxor; - // if (mode==5) dat2 = dat2; - if (mode==6) dat2 += extraxor; - - if (mode==2 || mode==6) dat2 = (dat2<<8)|(dat2>>8); - - m_sharedprotram[dst + x] = (dat2 << 8) | (dat2 >> 8); - } - } - break; - - // default: - // logerror ("DMA mode unknown!!!\nsrc:%4.4x, dst: %4.4x, size: %4.4x, mode: %4.4x\n", src, dst, size, mode); - } -} - void pgm_028_025_state::olds_protection_calculate_hold(int y, int z) // calculated in routine $12dbc2 in olds { unsigned short old = m_olds_prot_hold; @@ -285,65 +205,7 @@ WRITE16_MEMBER(pgm_028_025_state::olds_w ) case 0x03: { - UINT16 cmd = m_sharedprotram[0x3026 / 2]; - - // logerror ("command: %x\n", cmd); - - switch (cmd) - { - case 0x12: - { - UINT16 mode = m_sharedprotram[0x303e / 2]; // ? - UINT16 src = m_sharedprotram[0x306a / 2] >> 1; // ? - UINT16 dst = m_sharedprotram[0x3084 / 2] & 0x1fff; - UINT16 size = m_sharedprotram[0x30a2 / 2] & 0x1fff; - - IGS028_do_dma(src, dst, size, mode); - } - break; - - case 0x64: // incomplete? - { - UINT16 p1 = m_sharedprotram[0x3050 / 2]; - UINT16 p2 = m_sharedprotram[0x3082 / 2]; - UINT16 p3 = m_sharedprotram[0x3054 / 2]; - UINT16 p4 = m_sharedprotram[0x3088 / 2]; - - if (p2 == 0x02) - olds_write_reg(p1, olds_read_reg(p1) + 0x10000); - - switch (p4) - { - case 0xd: - olds_write_reg(p1,olds_read_reg(p3)); - break; - case 0x0: - olds_write_reg(p3,(olds_read_reg(p2))^(olds_read_reg(p1))); - break; - case 0xe: - olds_write_reg(p3,olds_read_reg(p3)+0x10000); - break; - case 0x2: - olds_write_reg(p1,(olds_read_reg(p2))+(olds_read_reg(p3))); - break; - case 0x6: - olds_write_reg(p3,(olds_read_reg(p2))&(olds_read_reg(p1))); - break; - case 0x1: - olds_write_reg(p2,olds_read_reg(p1)+0x10000); - break; - case 0x7: - olds_write_reg(p3,olds_read_reg(p1)); - break; - default: - break; - } - } - break; - - // default: - // logerror ("unemulated command!\n"); - } + m_igs028->IGS028_handle(); m_olds_cmd3 = ((data >> 4) + 1) & 0x3; } @@ -420,13 +282,7 @@ MACHINE_RESET_MEMBER(pgm_028_025_state,olds) { MACHINE_RESET_CALL_MEMBER(pgm); -// written by protection device -// there seems to be an auto-dma that writes from $401000-402573? - m_sharedprotram[0x1000/2] = 0x4749; // 'IGS.28' - m_sharedprotram[0x1002/2] = 0x2E53; - m_sharedprotram[0x1004/2] = 0x3832; - m_sharedprotram[0x3064/2] = 0xB315; // crc? } DRIVER_INIT_MEMBER(pgm_028_025_state,olds) @@ -434,6 +290,8 @@ DRIVER_INIT_MEMBER(pgm_028_025_state,olds) pgm_basic_init(); m_maincpu->space(AS_PROGRAM).install_readwrite_handler(0xdcb400, 0xdcb403, read16_delegate(FUNC(pgm_028_025_state::olds_r),this), write16_delegate(FUNC(pgm_028_025_state::olds_w),this)); + m_igs028->m_sharedprotram = m_sharedprotram; + m_olds_prot_hold = 0; m_olds_prot_hilo = 0; @@ -465,6 +323,8 @@ MACHINE_CONFIG_START( pgm_028_025_ol, pgm_028_025_state ) MCFG_CPU_MODIFY("maincpu") MCFG_CPU_PROGRAM_MAP(olds_mem) + MCFG_DEVICE_ADD("igs028", IGS028, 0) + MCFG_MACHINE_RESET_OVERRIDE(pgm_028_025_state,olds) MACHINE_CONFIG_END diff --git a/src/mame/mame.mak b/src/mame/mame.mak index b276368f793..222e0c084f9 100644 --- a/src/mame/mame.mak +++ b/src/mame/mame.mak @@ -1050,6 +1050,7 @@ $(MAMEOBJ)/igs.a: \ $(MACHINE)/pgmprot_igs025_igs028.o \ $(MACHINE)/igs025.o \ $(MACHINE)/igs022.o \ + $(MACHINE)/igs028.o \ $(MAMEOBJ)/irem.a: \ $(DRIVERS)/m10.o $(VIDEO)/m10.o \ |
