From 21efb0e47cebcf7d175a79bcf6eb700d484e0d32 Mon Sep 17 00:00:00 2001 From: AJR Date: Tue, 28 Jun 2022 14:41:16 -0400 Subject: Start moving devices out of src/mame/shared to more appropriate places --- scripts/src/bus.lua | 2 + scripts/src/cpu.lua | 2 + scripts/src/machine.lua | 22 + scripts/src/video.lua | 36 ++ scripts/target/mame/mame.lua | 4 + src/devices/bus/ata/gdrom.cpp | 577 +++++++++++++++++++++ src/devices/bus/ata/gdrom.h | 46 ++ src/devices/cpu/z80/mc8123.cpp | 416 +++++++++++++++ src/devices/cpu/z80/mc8123.h | 43 ++ src/devices/machine/bacta_datalogger.cpp | 218 ++++++++ src/devices/machine/bacta_datalogger.h | 39 ++ src/devices/machine/nmk112.cpp | 103 ++++ src/devices/machine/nmk112.h | 53 ++ src/devices/video/k051316.cpp | 304 +++++++++++ src/devices/video/k051316.h | 86 ++++ src/devices/video/k053936.cpp | 855 +++++++++++++++++++++++++++++++ src/devices/video/k053936.h | 60 +++ src/devices/video/tmap038.cpp | 263 ++++++++++ src/devices/video/tmap038.h | 114 +++++ src/mame/atlus/patapata.cpp | 2 +- src/mame/barcrest/mpu4.h | 3 +- src/mame/bfm/rastersp.cpp | 2 +- src/mame/jpm/guab.cpp | 3 +- src/mame/jpm/jpmimpct.h | 3 +- src/mame/jpm/jpmsys5.cpp | 3 +- src/mame/konami/88games.h | 2 +- src/mame/konami/ajax.cpp | 2 +- src/mame/konami/bottom9.cpp | 2 +- src/mame/konami/chqflag.h | 2 +- src/mame/konami/dbz.h | 2 +- src/mame/konami/divebomb.h | 2 +- src/mame/konami/konamigx.h | 2 +- src/mame/konami/overdriv.cpp | 4 +- src/mame/konami/plygonet.cpp | 2 +- src/mame/konami/rollerg.cpp | 2 +- src/mame/konami/rungun.h | 2 +- src/mame/konami/tmnt.h | 2 +- src/mame/konami/ultraman.h | 2 +- src/mame/konami/wecleman.h | 2 +- src/mame/metro/metro.h | 3 +- src/mame/misc/cave.cpp | 3 +- src/mame/misc/cave.h | 4 +- src/mame/misc/freekick.cpp | 3 +- src/mame/misc/mcatadv.h | 4 +- src/mame/nmk/nmk16.cpp | 3 +- src/mame/nmk/powerins.cpp | 3 +- src/mame/nmk/quizpani.h | 2 +- src/mame/sanritsu/chinsan.cpp | 3 +- src/mame/sega/naomigd.h | 2 +- src/mame/sega/segae.cpp | 2 +- src/mame/sega/segas16b.cpp | 2 +- src/mame/sega/system1.cpp | 2 +- src/mame/segacons/dccons.cpp | 2 +- src/mame/segacons/dccons.h | 1 - src/mame/shared/bacta_datalogger.cpp | 218 -------- src/mame/shared/bacta_datalogger.h | 39 -- src/mame/shared/gdrom.cpp | 577 --------------------- src/mame/shared/gdrom.h | 46 -- src/mame/shared/k051316.cpp | 304 ----------- src/mame/shared/k051316.h | 86 ---- src/mame/shared/k053936.cpp | 855 ------------------------------- src/mame/shared/k053936.h | 60 --- src/mame/shared/mc8123.cpp | 416 --------------- src/mame/shared/mc8123.h | 43 -- src/mame/shared/nmk112.cpp | 103 ---- src/mame/shared/nmk112.h | 53 -- src/mame/shared/tmap038.cpp | 263 ---------- src/mame/shared/tmap038.h | 114 ----- src/mame/upl/ninjakd2.cpp | 3 +- src/mame/vsystem/crshrace.h | 3 +- src/mame/vsystem/f1gp.h | 3 +- src/mame/vsystem/suprslam.h | 3 +- src/mame/vsystem/tail2nos.cpp | 3 +- 73 files changed, 3283 insertions(+), 3237 deletions(-) create mode 100644 src/devices/bus/ata/gdrom.cpp create mode 100644 src/devices/bus/ata/gdrom.h create mode 100644 src/devices/cpu/z80/mc8123.cpp create mode 100644 src/devices/cpu/z80/mc8123.h create mode 100644 src/devices/machine/bacta_datalogger.cpp create mode 100644 src/devices/machine/bacta_datalogger.h create mode 100644 src/devices/machine/nmk112.cpp create mode 100644 src/devices/machine/nmk112.h create mode 100644 src/devices/video/k051316.cpp create mode 100644 src/devices/video/k051316.h create mode 100644 src/devices/video/k053936.cpp create mode 100644 src/devices/video/k053936.h create mode 100644 src/devices/video/tmap038.cpp create mode 100644 src/devices/video/tmap038.h delete mode 100644 src/mame/shared/bacta_datalogger.cpp delete mode 100644 src/mame/shared/bacta_datalogger.h delete mode 100644 src/mame/shared/gdrom.cpp delete mode 100644 src/mame/shared/gdrom.h delete mode 100644 src/mame/shared/k051316.cpp delete mode 100644 src/mame/shared/k051316.h delete mode 100644 src/mame/shared/k053936.cpp delete mode 100644 src/mame/shared/k053936.h delete mode 100644 src/mame/shared/mc8123.cpp delete mode 100644 src/mame/shared/mc8123.h delete mode 100644 src/mame/shared/nmk112.cpp delete mode 100644 src/mame/shared/nmk112.h delete mode 100644 src/mame/shared/tmap038.cpp delete mode 100644 src/mame/shared/tmap038.h diff --git a/scripts/src/bus.lua b/scripts/src/bus.lua index 46b7461763f..443fe4c3922 100644 --- a/scripts/src/bus.lua +++ b/scripts/src/bus.lua @@ -463,6 +463,8 @@ if (BUSES["ATA"]~=null) then MAME_DIR .. "src/devices/bus/ata/atapihle.h", MAME_DIR .. "src/devices/bus/ata/cr589.cpp", MAME_DIR .. "src/devices/bus/ata/cr589.h", + MAME_DIR .. "src/devices/bus/ata/gdrom.cpp", + MAME_DIR .. "src/devices/bus/ata/gdrom.h", MAME_DIR .. "src/devices/bus/ata/idehd.cpp", MAME_DIR .. "src/devices/bus/ata/idehd.h", MAME_DIR .. "src/devices/bus/ata/px320a.cpp", diff --git a/scripts/src/cpu.lua b/scripts/src/cpu.lua index a560750b3d4..03770359e82 100644 --- a/scripts/src/cpu.lua +++ b/scripts/src/cpu.lua @@ -2720,6 +2720,8 @@ if (CPUS["Z80"]~=null or CPUS["KC80"]~=null) then MAME_DIR .. "src/devices/cpu/z80/ez80.h", MAME_DIR .. "src/devices/cpu/z80/lz8420m.cpp", MAME_DIR .. "src/devices/cpu/z80/lz8420m.h", + MAME_DIR .. "src/devices/cpu/z80/mc8123.cpp", + MAME_DIR .. "src/devices/cpu/z80/mc8123.h", MAME_DIR .. "src/devices/cpu/z80/r800.cpp", MAME_DIR .. "src/devices/cpu/z80/r800.h", } diff --git a/scripts/src/machine.lua b/scripts/src/machine.lua index 60fd77428dd..3ba68547c83 100644 --- a/scripts/src/machine.lua +++ b/scripts/src/machine.lua @@ -5018,6 +5018,28 @@ if (MACHINES["AT_MB"]~=null) then } end +--------------------------------------------------- +-- +--@src/devices/machine/bacta_datalogger.h,MACHINES["BACTA_DATALOGGER"] = true +--------------------------------------------------- +if (MACHINES["BACTA_DATALOGGER"]~=null) then + files { + MAME_DIR .. "src/devices/machine/bacta_datalogger.cpp", + MAME_DIR .. "src/devices/machine/bacta_datalogger.h", + } +end + +--------------------------------------------------- +-- +--@src/devices/machine/nmk112.h,MACHINES["NMK112"] = true +--------------------------------------------------- +if (MACHINES["NMK112"]~=null) then + files { + MAME_DIR .. "src/devices/machine/nmk112.cpp", + MAME_DIR .. "src/devices/machine/nmk112.h", + } +end + --------------------------------------------------- -- --@src/devices/machine/saa7191.h,MACHINES["SAA7191"] = true diff --git a/scripts/src/video.lua b/scripts/src/video.lua index 12f4f55b2a8..5fdc340d250 100644 --- a/scripts/src/video.lua +++ b/scripts/src/video.lua @@ -591,6 +591,30 @@ if (VIDEOS["IMS_CVC"]~=null) then } end +-------------------------------------------------- +-- +--@src/devices/video/k051316.h,VIDEOS["K051316"] = true +-------------------------------------------------- + +if (VIDEOS["K051316"]~=null) then + files { + MAME_DIR .. "src/devices/video/k051316.cpp", + MAME_DIR .. "src/devices/video/k051316.h", + } +end + +-------------------------------------------------- +-- +--@src/devices/video/k053936.h,VIDEOS["K053936"] = true +-------------------------------------------------- + +if (VIDEOS["K053936"]~=null) then + files { + MAME_DIR .. "src/devices/video/k053936.cpp", + MAME_DIR .. "src/devices/video/k053936.h", + } +end + -------------------------------------------------- -- --@src/devices/video/lc7582.h,VIDEOS["LC7582"] = true @@ -1000,6 +1024,18 @@ if (VIDEOS["TLC34076"]~=null) then } end +-------------------------------------------------- +-- +--@src/devices/video/tmap038.h,VIDEOS["TMAP038"] = true +-------------------------------------------------- + +if (VIDEOS["TMAP038"]~=null) then + files { + MAME_DIR .. "src/devices/video/tmap038.cpp", + MAME_DIR .. "src/devices/video/tmap038.h", + } +end + -------------------------------------------------- -- --@src/devices/video/tms34061.h,VIDEOS["TMS34061"] = true diff --git a/scripts/target/mame/mame.lua b/scripts/target/mame/mame.lua index ee740f62de6..8a02db33995 100644 --- a/scripts/target/mame/mame.lua +++ b/scripts/target/mame/mame.lua @@ -393,6 +393,8 @@ VIDEOS["I82730"] = true VIDEOS["I8275"] = true VIDEOS["IMS_CVC"] = true VIDEOS["JANGOU_BLITTER"] = true +VIDEOS["K051316"] = true +VIDEOS["K053936"] = true VIDEOS["LC7582"] = true VIDEOS["LC7985"] = true VIDEOS["M50458"] = true @@ -436,6 +438,7 @@ VIDEOS["T6963C"] = true VIDEOS["T6A04"] = true VIDEOS["TEA1002"] = true VIDEOS["TLC34076"] = true +VIDEOS["TMAP038"] = true VIDEOS["TMS34061"] = true VIDEOS["TMS3556"] = true VIDEOS["TMS9927"] = true @@ -512,6 +515,7 @@ MACHINES["AT_KEYBC"] = true MACHINES["AT_MB"] = true MACHINES["AUTOCONFIG"] = true MACHINES["AY31015"] = true +MACHINES["BACTA_DATALOGGER"] = true MACHINES["BANKDEV"] = true MACHINES["BIM68153"] = true MACHINES["BITMAP_PRINTER"] = true diff --git a/src/devices/bus/ata/gdrom.cpp b/src/devices/bus/ata/gdrom.cpp new file mode 100644 index 00000000000..59a7d154d56 --- /dev/null +++ b/src/devices/bus/ata/gdrom.cpp @@ -0,0 +1,577 @@ +// license:BSD-3-Clause +// copyright-holders:smf, Angelo Salese +/*************************************************************************** + + gdrom.c - Implementation of the Sega GD-ROM device + +***************************************************************************/ + +#include "emu.h" +#include "gdrom.h" + +#define LOG_WARN (1U << 1) +#define LOG_CMD (1U << 2) +#define LOG_XFER (1U << 3) + +#define VERBOSE (LOG_WARN | LOG_CMD) +//#define LOG_OUTPUT_STREAM std::cout +#include "logmacro.h" + +#define LOGWARN(...) LOGMASKED(LOG_WARN, __VA_ARGS__) +#define LOGCMD(...) LOGMASKED(LOG_CMD, __VA_ARGS__) +#define LOGXFER(...) LOGMASKED(LOG_XFER, __VA_ARGS__) + +#define GDROM_BUSY_STATE 0x00 +#define GDROM_PAUSE_STATE 0x01 +#define GDROM_STANDBY_STATE 0x02 +#define GDROM_PLAY_STATE 0x03 +#define GDROM_SEEK_STATE 0x04 +#define GDROM_SCAN_STATE 0x05 +#define GDROM_OPEN_STATE 0x06 +#define GDROM_NODISC_STATE 0x07 +#define GDROM_RETRY_STATE 0x08 +#define GDROM_ERROR_STATE 0x09 + + +/* + Officially not documented security-related packet commands: + + SYS_CHK_SECU (70h) Media security check + Parameters: 1byte - R0011111, R - "recheck" (it seems actual security check performed automatically at drive power on or when disc was inserted, so normally this and next command returns result of already performed check. + however, when MSB R bit is 1 will be forced media security recheck) + Result: none + SYS_REQ_SECU (71h) Request security data + Parameters: 1byte - always 0x1f + Result: a bit less than 1Kbyte chunk of data (length vary each time), contains real command reply obfuscated, which is extracted by such code: + + u8 reply[], real_reply[]; + for (u32 i = 0, offset = 0; i < length; i++) + { + offset++; + u32 skip = reply[offset] - 2; // normally skip value is < 0x10, might be used to identify real reply length + offset += skip; + real_reply[i] = reply[offset++]; + } + + Real reply is 43 byte: + struct sec_reply { + u8 check_result; // 0x1f - valid GD-ROM, 0x10 - valid Mil-CD (in this case following char[] fields is empty, 0x00-filled) + char key_id[10]; // presumable Disc ID (T-xxxxxx or HDR-xxxxx etc) + char key_maker_id[16]; // presumable "SEGA ENTERPRISES" + char hard_id[16]; // presumable "SEGA SEGAKATANA " + }; + + *_id fields names came from Dev.box "Checker BIOS" disassembly, contents meaning is guesswork because all the reply dumps we have now was dumped with Mil-CD disc inserted but not GD-ROM. + Presumable these data somehow encoded in GD-ROM disc HD area Lead-in (or Security Ring area ?), and compared with data in LD area IP.BIN by GD-drive firmware, + as described in Sega patent EP0935242A1 https://patents.google.com/patent/EP0935242A1 + + Dreamcast BIOS code verify only 1st result byte, if it's 5th bit (0x10) == 1. + Naomi DIMM firmware verify if result byte equal to 0x1f. + + SYS_CHG_COMD (72h) ??? Authentication for next command ? + Parameters: 1byte, probably key/password, in retail Dreamcast - 5th byte of unit SN# (located in flash ROM at 1A05Ah), 0 in Dev.box checker BIOS. + Result: none + + SYS_REQ_COMD (73h) Request command list + Parameters: none + Result: chunk of data where obfuscated real reply, see command 71. + real result: 14 bytes - codes of all regular (not security) packet commands supported by drive (00 10 11 12 13 14 15 16 20 21 22 30 31 40). + + Dreamcast BIOS SysCalls contain commands 0x72/73 routine, but it seems not used at practice. +*/ + +static const uint8_t GDROM_Cmd71_Reply[] = +{ + 0x96, 0x0B, 0x45, 0xF0, 0x7E, 0xFF, 0x3D, 0x06, 0x4D, 0x7D, 0x10, 0xBF, 0x07, 0x00, 0x73, 0xCF, + 0x9C, 0x00, 0xBC, 0x0C, 0x1C, 0xAF, 0x1C, 0x30, 0xE7, 0xA7, 0x03, 0xA8, 0x98, 0x00, 0xBD, 0x0F, + 0xBD, 0x5B, 0xAA, 0x50, 0x23, 0x39, 0x31, 0x10, 0x0E, 0x69, 0x13, 0xE5, 0x00, 0xD2, 0x0D, 0x66, + 0x54, 0xBF, 0x5F, 0xFD, 0x37, 0x74, 0xF4, 0x5B, 0x22, 0x00, 0xC6, 0x09, 0x0F, 0xCA, 0x93, 0xE8, + 0xA4, 0xAB, 0x00, 0x61, 0x0E, 0x2E, 0xE1, 0x4B, 0x76, 0x8B, 0x6A, 0xA5, 0x9C, 0xE6, 0x23, 0xC4, + 0x00, 0x4B, 0x06, 0x1B, 0x91, 0x01, 0x00, 0xE2, 0x0D, 0xCF, 0xCA, 0x38, 0x3A, 0xB9, 0xE7, 0x91, + 0xE5, 0xEF, 0x4B, 0x00, 0xD6, 0x09, 0xD3, 0x68, 0x3E, 0xC4, 0xAF, 0x2D, 0x00, 0x2A, 0x0D, 0xF9, + 0xFC, 0x78, 0xED, 0xAE, 0x99, 0xB3, 0x32, 0x5A, 0xE7, 0x00, 0x4C, 0x0A, 0x22, 0x97, 0x5B, 0x82, + 0x06, 0x7A, 0x4C, 0x00, 0x42, 0x0E, 0x57, 0x78, 0x46, 0xF5, 0x20, 0xFC, 0x6B, 0xCB, 0x01, 0x5B, + 0x86, 0x00, 0xE4, 0x0E, 0xB2, 0x26, 0xCD, 0x71, 0xE3, 0xA5, 0x33, 0x06, 0x8E, 0x9A, 0x50, 0x00, + 0x07, 0x07, 0xF5, 0x34, 0xEF, 0xE6, 0x00, 0x32, 0x0F, 0x13, 0x41, 0x59, 0x56, 0x0F, 0x02, 0x38, + 0x2A, 0x64, 0x2A, 0x07, 0x3E, 0x00, 0x52, 0x11, 0x2A, 0x1D, 0x5F, 0x76, 0x66, 0xA0, 0xB2, 0x2F, + 0x97, 0xC7, 0x5E, 0x6E, 0x52, 0xE2, 0x00, 0x58, 0x09, 0xCA, 0x89, 0xA5, 0xDF, 0x0A, 0xDE, 0x00, + 0x50, 0x06, 0x49, 0xB8, 0xB4, 0x00, 0x77, 0x05, 0x24, 0xE8, 0x00, 0xBB, 0x0C, 0x91, 0x89, 0xA2, + 0x8B, 0x62, 0xDE, 0x6A, 0xC6, 0x60, 0x00, 0xE7, 0x0F, 0x0F, 0x11, 0x96, 0x55, 0xD2, 0xBF, 0xE6, + 0x48, 0x0B, 0x5C, 0xAB, 0xDC, 0x00, 0xBA, 0x0A, 0x30, 0xD7, 0x48, 0x0E, 0x78, 0x63, 0x0C, 0x00, + 0xD2, 0x0D, 0xFB, 0x8A, 0xA3, 0xFE, 0xF8, 0x3A, 0xDD, 0x88, 0xA9, 0x4B, 0x00, 0xA2, 0x0A, 0x75, + 0x5D, 0x0D, 0x37, 0x24, 0xC5, 0x9D, 0x00, 0xF7, 0x0B, 0x25, 0xEF, 0xDB, 0x41, 0xE0, 0x52, 0x3E, + 0x4E, 0x00, 0xB7, 0x03, 0x00, 0xE5, 0x11, 0xB9, 0xDE, 0x5A, 0x57, 0xCF, 0xB9, 0x1A, 0xFC, 0x7F, + 0x26, 0xEE, 0x7B, 0xCD, 0x2B, 0x00, 0x4B, 0x08, 0xB8, 0x09, 0x70, 0x6A, 0x9F, 0x00, 0x4B, 0x11, + 0x8C, 0x15, 0x87, 0xA3, 0x05, 0x4F, 0x37, 0x8E, 0x63, 0xDE, 0xEF, 0x39, 0xFC, 0x4B, 0x00, 0xAB, + 0x10, 0x0B, 0x91, 0xAA, 0x0F, 0xE1, 0xE9, 0xAE, 0x69, 0x3A, 0xF8, 0x03, 0x69, 0xD2, 0x00, 0xE2, + 0x07, 0xC1, 0x5C, 0x3D, 0x82, 0x00, 0xA9, 0x08, 0x68, 0xC4, 0xAD, 0x2E, 0xD1, 0x00, 0xF7, 0x0E, + 0xC6, 0x47, 0xC8, 0xCD, 0x8E, 0x7C, 0x00, 0x5C, 0x95, 0xB9, 0xF4, 0x00, 0xE3, 0x04, 0x5B, 0x00, + 0x74, 0x07, 0x65, 0xC7, 0x84, 0x8E, 0x00, 0xC6, 0x07, 0x61, 0x80, 0x44, 0x3F, 0x00, 0xC8, 0x0E, + 0x72, 0x78, 0x47, 0xD3, 0xC2, 0x4D, 0xAF, 0xC0, 0x54, 0x13, 0x31, 0x00, 0xF7, 0x0D, 0x48, 0xD8, + 0xE2, 0x92, 0x9F, 0x7F, 0x2F, 0x44, 0x68, 0x33, 0x00, 0x0D, 0x10, 0xAB, 0xFE, 0xEA, 0x8E, 0x19, + 0x81, 0xF8, 0x6F, 0x7C, 0xDE, 0xE1, 0xB3, 0x06, 0x00, 0x4D, 0x11, 0x66, 0xAE, 0x4C, 0xF9, 0xB7, + 0x2F, 0xEE, 0xB0, 0x8E, 0x7E, 0xE1, 0x8D, 0x95, 0x6F, 0x00, 0xF4, 0x0D, 0x88, 0x9D, 0xCA, 0xE3, + 0xC4, 0xB2, 0x47, 0xBB, 0xA0, 0x69, 0x00, 0xF3, 0x0B, 0x48, 0x17, 0x41, 0x64, 0xA0, 0x0E, 0x71, + 0x82, 0x00, 0x34, 0x1E, 0x18, 0x4D, 0x85, 0x80, 0x4C, 0xA9, 0x0B, 0x66, 0x9B, 0x75, 0x13, 0x61, + 0x70, 0x27, 0x81, 0x7A, 0x02, 0xCD, 0x57, 0xAB, 0xDF, 0x02, 0x93, 0x52, 0x83, 0xDF, 0x48, 0xA8, + 0xA6, 0x9E, 0x74, 0x6F, 0x89, 0x03, 0x28, 0x25, 0x52, 0x96, 0xFF, 0x67, 0x7A, 0xD8, 0x3C, 0xB1, + 0x2C, 0x46, 0x84, 0xEF, 0xE1, 0xC1, 0xC6, 0xC9, 0xDC, 0x96, 0xAA, 0xA9, 0xC4, 0x82, 0x58, 0x27, + 0x57, 0x75, 0x67, 0x34, 0xFB, 0x3B, 0x25, 0xBF, 0xFB, 0x3B, 0xF6, 0x13, 0xEC, 0x96, 0xE5, 0x16, + 0x26, 0xFD, 0xA8, 0xDA, 0x1B, 0xC6, 0x50, 0x7F, 0x47, 0xFF, 0x08, 0x55, 0x08, 0xED, 0x00, 0x93, + 0x9B, 0xC4, 0x71, 0x67, 0xEC, 0xA6, 0xCC, 0x16, 0x20, 0x87, 0x47, 0x07, 0xA6, 0x00, 0x79, 0x5D, + 0x4F, 0xAB, 0xA1, 0x6F, 0x7A, 0x6B, 0x27, 0xC4, 0xDA, 0xA3, 0xC3, 0x94, 0x4F, 0x7F, 0xF3, 0xE5, + 0x1B, 0x6F, 0xCC, 0xE5, 0xF0, 0xE5, 0x9D, 0xC9, 0xAE, 0xFD, 0x39, 0xAC, 0x4C, 0xE5, 0x58, 0x83, + 0x25, 0x65, 0x92, 0x74, 0x9E, 0x81, 0xA0, 0xB6, 0xA9, 0x02, 0x9B, 0x07, 0xB6, 0xE7, 0x79, 0x57, + 0xD9, 0x4A, 0xCE, 0xFA, 0xB4, 0x94, 0x05, 0xCC, 0x86, 0x3C, 0xDD, 0x06, 0xCD, 0xA6, 0x24, 0x24, + 0xFA, 0xC1, 0xF9, 0x48, 0xC9, 0x0C, 0x6C, 0xC4, 0x96, 0x82, 0x17, 0xF6, 0x31, 0x09, 0xC4, 0xE2, + 0x77, 0xFD, 0xCF, 0x46, 0x18, 0xB2, 0x5F, 0x01, 0x6B, 0xD1, 0x7B, 0x56, 0xB8, 0x94, 0x4A, 0xE5, + 0x6C, 0x19, 0xF0, 0xC0, 0xB6, 0x70, 0x93, 0xF7, 0xD3, 0xD1, 0x2B, 0x6E, 0x7C, 0x53, 0x6D, 0x85, + 0xD1, 0x0C, 0x8B, 0x77, 0xEE, 0x90, 0xDA, 0x15, 0x55, 0xE0, 0x58, 0x09, 0x56, 0xFC, 0x31, 0x9F, + 0xAF, 0x46, 0xCB, 0xC3, 0x8D, 0x71, 0x75, 0xF2, 0x2C, 0xC3, 0xBB, 0xA1, 0xC4, 0xCF, 0x27, 0x56, + 0x7C, 0x9B, 0xFE, 0xAF, 0x3E, 0x4E, 0xB4, 0xCD, 0x6A, 0xAA, 0xF5, 0xF3, 0xE3, 0x22, 0x82, 0xE1, + 0xA5, 0x68, 0xB3, 0xDB, 0x8F, 0x9E, 0x5E, 0x7B, 0x90, 0xF0, 0x79, 0x3F, 0x52, 0x8C, 0x61, 0x88, + 0x76, 0xAE, 0x14, 0x63, 0x19, 0x0F, 0x1D, 0xCE, 0xA1, 0x63, 0x10, 0xB2, 0xE2, 0xD7, 0x94, 0xB1, + 0x33, 0xCB, 0x28, 0x85, 0x7D, 0x9B, 0xF5, 0xF4, 0x25, 0x50, 0x9B, 0xDB, 0x35, 0xA5, 0xB0, 0x9C, + 0x09, 0x92, 0xE3, 0x31, 0x40, 0xAB, 0x4D, 0xF4, 0x35, 0xE8, 0xB3, 0x0A, 0x21, 0xC3, 0x86, 0x9C, + 0xCB, 0x29, 0xA4, 0x77, 0x57, 0xBC, 0xD8, 0xDA, 0xA5, 0x82, 0x80, 0xE8, 0xCF, 0x72, 0x81, 0xAD, + 0x2E, 0x28, 0xFF, 0xD8, 0xB6, 0xD1, 0x2B, 0x97, 0x00, 0xFF, 0xE1, 0x06, 0x44, 0x39, 0x1C, 0x4B, + 0xAB, 0x19, 0x5B, 0x4D, 0xD6, 0x3E, 0x1B, 0x5C, 0x64, 0xBB, 0x32, 0x68, 0xF5, 0x7C, 0xC9, 0x9E, + 0xE8, 0xB4, 0x29, 0x1B, 0x7F, 0x4D, 0x80, 0x80, 0x7E, 0x8B, 0x1C, 0x0A, 0xE6, 0x9A, 0xBF, 0x49, + 0x1E, 0xC5, 0xB6, 0x67, 0x7D, 0x05, 0xE4, 0x90, 0x40, 0x4B, 0xAF, 0x9B, 0x52, 0xDE, 0x17, 0x80, + 0x81, 0x56, 0xEA, 0x3A, 0x53, 0x82, 0x8C, 0x62, 0xFB, 0x96, 0x97, 0x6F, 0xC1, 0x16, 0x78, 0xD4, + 0x7B, 0xE7, 0xB9, 0x5A, 0x2A, 0xEB, 0x87, 0x68, 0x33, 0xD3, 0x31, 0x45, 0xFA, 0xFE, 0xF4, 0x1C, + 0x90, 0x86, 0x73, 0x77, 0xD9, 0xA9, 0xD1, 0x4A, 0x4A, 0xCF, 0xAE, 0x23, 0xDB, 0xF9, 0x09, 0xD8, + 0x18, 0xDC, 0x6A, 0x0D, 0xE4, 0x19, 0x8C, 0x65, 0xC6, 0x64, 0xC7, 0xDC, 0xA9, 0xE3, 0x91, 0xB1, + 0x4C, 0xC8, 0xC1, 0x9E, 0x3B, 0x7F, 0xCB, 0xA3, 0xCF, 0xDD, 0xF0, 0x1D, 0x07, 0x6E, 0xDC, 0xCE, + 0x0D, 0xCD, 0x7E, 0x1E, 0x55, 0x11, 0x8B, 0xDF, 0x3A, 0xAB, 0xB6, 0x3B, 0x6E, 0x52, 0x7F, 0xA7, + 0x00, 0xD1, 0x33, 0xBE, 0xF2, 0x9B, 0xFC, 0x4A, 0xCF, 0x9D, 0x8F, 0xC6, 0xC4, 0x7B, 0xDA, 0xE7, + 0x2A, 0x1C, 0x26, 0x6E +}; + + +void gdrom_device::device_reset() +{ + static const uint8_t GDROM_Def_Cmd11_Reply[32] = + { + 0x00, 0x00, 0x00, 0x00, 0x00, 0xB4, 0x19, 0x00, 0x00, 0x08, 0x53, 0x45, 0x20, 0x20, 0x20, 0x20, + 0x20, 0x20, 0x52, 0x65, 0x76, 0x20, 0x36, 0x2E, 0x34, 0x32, 0x39, 0x39, 0x30, 0x33, 0x31, 0x36 + }; + + for(int i = 0;i<32;i++) + GDROM_Cmd11_Reply[i] = GDROM_Def_Cmd11_Reply[i]; + + atapi_cdrom_device::device_reset(); +} + +// scsicd_exec_command +// +// Execute a SCSI command. + +void gdrom_device::ExecCommand() +{ + switch ( command[0] ) + { + case 0x11: // REQ_MODE + m_phase = SCSI_PHASE_DATAIN; + m_status_code = SCSI_STATUS_CODE_GOOD; + LOGCMD("REQ_MODE %02x %02x %02x %02x %02x %02x\n", + command[0], command[1], + command[2], command[3], + command[4], command[5] + ); +// if (SCSILengthFromUINT8( &command[ 4 ] ) < 32) return -1; + transferOffset = command[2]; + m_transfer_length = SCSILengthFromUINT8( &command[ 4 ] ); + break; + + case 0x12: // SET_MODE + m_phase = SCSI_PHASE_DATAOUT; + m_status_code = SCSI_STATUS_CODE_GOOD; + //transferOffset = command[2]; + m_transfer_length = SCSILengthFromUINT8( &command[ 4 ] ); + LOGCMD("SET_MODE %02x %02x\n", command[2], command[4]); + break; + + case 0x30: // CD_READ + if (command[1] & 1) + { + m_transfer_length = 0; + throw emu_fatalerror("GDROM: MSF mode used for CD_READ, unsupported"); + } + else + { + m_lba = (command[2]<<16 | command[3]<<8 | command[4]) - 150; + m_blocks = command[8]<<16 | command[9]<<8 | command[10]; + + read_type = (command[1] >> 1) & 7; + data_select = (command[1]>>4) & 0xf; + + if (read_type != 2) // mode 1 + { + throw emu_fatalerror("GDROM: Unhandled read_type %d", read_type); + } + + if (data_select != 2) // just sector data + { + throw emu_fatalerror("GDROM: Unhandled data_select %d", data_select); + } + + LOGCMD("CD_READ %02x %02x\n", command[2], command[4]); + LOGCMD(" LBA %x for %d blocks (%d bytes, read type %d, data select %d)\n", + m_lba, m_blocks, + m_blocks * m_sector_bytes, read_type, data_select + ); + + if (m_num_subblocks > 1) + { + m_cur_subblock = m_lba % m_num_subblocks; + m_lba /= m_num_subblocks; + } + else + { + m_cur_subblock = 0; + } + + if (m_cdda != nullptr) + { + m_cdda->stop_audio(); + } + + m_phase = SCSI_PHASE_DATAIN; + m_status_code = SCSI_STATUS_CODE_GOOD; + m_transfer_length = m_blocks * m_sector_bytes; + } + break; + + // READ TOC (GD-ROM ver.) + case 0x14: + { + if (m_cdrom == nullptr) + { + m_phase = SCSI_PHASE_STATUS; + m_status_code = SCSI_STATUS_CODE_CHECK_CONDITION; + m_transfer_length = 0; + break; + } + + // TODO: is this correct? + int start_trk = command[2]; + int end_trk = m_cdrom->get_last_track(); + int length; + int allocation_length = SCSILengthFromUINT16( &command[ 3 ] ); + + if( start_trk == 0 ) + { + start_trk = 1; + } + if( start_trk == 0xaa ) + { + end_trk = start_trk; + } + + length = 4 + ( 8 * ( ( end_trk - start_trk ) + 1 ) ); + if( length > allocation_length ) + { + length = allocation_length; + } + else if( length < 4 ) + { + length = 4; + } + + if (m_cdda != nullptr) + { + m_cdda->stop_audio(); + } + + m_phase = SCSI_PHASE_DATAIN; + m_status_code = SCSI_STATUS_CODE_GOOD; + m_transfer_length = length; + break; + } + + case 0x70: // security check, return no data, always followed by cmd 0x71, command[1] parameter can be 0x1f or 0x9f + m_phase = SCSI_PHASE_STATUS; + m_status_code = SCSI_STATUS_CODE_GOOD; + m_transfer_length = 0; + break; + + case 0x71: + m_phase = SCSI_PHASE_DATAIN; + m_status_code = SCSI_STATUS_CODE_GOOD; + m_transfer_length = sizeof(GDROM_Cmd71_Reply); + break; + + case 0x40: + if(command[1] & 0xf) + { + m_phase = SCSI_PHASE_DATAIN; + m_status_code = SCSI_STATUS_CODE_GOOD; + m_transfer_length = 0xe; + } + else + { + LOGWARN("command 0x40: unhandled subchannel request\n"); + } + break; + + default: + t10mmc::ExecCommand(); + break; + } +} + +// scsicd_read_data +// +// Read data from the device resulting from the execution of a command + +void gdrom_device::ReadData( uint8_t *data, int dataLength ) +{ + int i; + uint8_t tmp_buffer[2048]; + + switch ( command[0] ) + { + case 0x11: // REQ_MODE + LOGCMD("REQ_MODE dataLength %d\n", dataLength); + memcpy(data, &GDROM_Cmd11_Reply[transferOffset], (dataLength >= 32-transferOffset) ? 32-transferOffset : dataLength); + break; + + case 0x30: // CD_READ + LOGCMD("CD_READ read %x dataLength,\n", dataLength); + if ((m_cdrom) && (m_blocks)) + { + while (dataLength > 0) + { + if (!m_cdrom->read_data(m_lba, tmp_buffer, cdrom_file::CD_TRACK_MODE1)) + { + LOGWARN("CD read error!\n"); + } + + LOGXFER("True LBA: %d, buffer half: %d\n", m_lba, m_cur_subblock * m_sector_bytes); + + memcpy(data, &tmp_buffer[m_cur_subblock * m_sector_bytes], m_sector_bytes); + + m_cur_subblock++; + if (m_cur_subblock >= m_num_subblocks) + { + m_cur_subblock = 0; + + m_lba++; + m_blocks--; + } + + m_last_lba = m_lba; + dataLength -= m_sector_bytes; + data += m_sector_bytes; + } + } + break; + + case 0x14: // READ TOC (GD-ROM ver.) + /* + Track numbers are problematic here: 0 = lead-in, 0xaa = lead-out. + That makes sense in terms of how real-world CDs are referred to, but + our internal routines for tracks use "0" as track 1. That probably + should be fixed... + */ + LOGCMD("READ TOC format = %d time=%d\n", + command[2] & 0xf, (command[1] >> 1) & 1 + ); + switch (command[2] & 0x0f) + { + case 0: // normal + { + int start_trk; + int end_trk; + int len; + int in_len; + int dptr; + uint32_t tstart; + + start_trk = command[2]; + if( start_trk == 0 ) + { + start_trk = 1; + } + + end_trk = m_cdrom->get_last_track(); + len = (end_trk * 8) + 2; + + // the returned TOC DATA LENGTH must be the full amount, + // regardless of how much we're able to pass back due to in_len + dptr = 0; + data[dptr++] = (len>>8) & 0xff; + data[dptr++] = (len & 0xff); + data[dptr++] = 1; + data[dptr++] = end_trk; + + if( start_trk == 0xaa ) + { + end_trk = 0xaa; + } + + in_len = command[3]<<8 | command[4]; + + for (i = start_trk; i <= end_trk; i++) + { + int cdrom_track = i; + if( cdrom_track != 0xaa ) + { + cdrom_track--; + } + + if( dptr >= in_len ) + { + break; + } + + data[dptr++] = 0; + data[dptr++] = m_cdrom->get_adr_control(cdrom_track); + data[dptr++] = i; + data[dptr++] = 0; + + tstart = m_cdrom->get_track_start(cdrom_track); + if ((command[1]&2)>>1) + tstart = cdrom_file::lba_to_msf(tstart); + data[dptr++] = (tstart>>24) & 0xff; + data[dptr++] = (tstart>>16) & 0xff; + data[dptr++] = (tstart>>8) & 0xff; + data[dptr++] = (tstart & 0xff); + } + + break; + } + default: + LOGWARN("Unhandled READ TOC format %d\n", command[2]&0xf); + break; + } + break; + + case 0x71: + LOGCMD("SYS_REQ_SECU\n"); + memcpy(data, &GDROM_Cmd71_Reply[0], sizeof(GDROM_Cmd71_Reply)); + if (is_real_gdrom_disc) + data[10] = 0x1f; // needed by dimm board firmware + break; + + case 0x40: // Get Subchannel status + data[0] = 0; // Reserved + data[1] = 0x15; // Audio Playback status (todo) + data[2] = 0; + data[3] = 0x0e; // header size + data[4] = 0; // ? + data[5] = 1; // Track Number + data[6] = 1; // gap #1 + data[7] = 0; // ? + data[8] = 0; // ? + data[9] = 0; // ? + data[0xa] = 0; // ? + data[0xb] = 0; // FAD >> 16 + data[0xc] = 0; // FAD >> 8 + data[0xd] = 0x96; // FAD >> 0 + break; + + default: + t10mmc::ReadData( data, dataLength ); + break; + } +} + +// scsicd_write_data +// +// Write data to the CD-ROM device as part of the execution of a command + +void gdrom_device::WriteData( uint8_t *data, int dataLength ) +{ + switch (command[ 0 ]) + { + case 0x12: // SET_MODE + memcpy(&GDROM_Cmd11_Reply[transferOffset], data, (dataLength >= 32-transferOffset) ? 32-transferOffset : dataLength); + break; + + default: + t10mmc::WriteData( data, dataLength ); + break; + } +} + +void gdrom_device::SetDevice(void *device) +{ + t10mmc::SetDevice(device); + + // try to find if the mounted chd is from an actual gd-rom disc + if (m_cdrom) + if (m_cdrom->get_toc().flags & cdrom_file::CD_FLAG_GDROM) + is_real_gdrom_disc = true; +} + +// device type definition +DEFINE_DEVICE_TYPE(GDROM, gdrom_device, "gdrom", "GD-ROM") + +gdrom_device::gdrom_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : + atapi_cdrom_device(mconfig, GDROM, tag, owner, clock), + is_real_gdrom_disc(false) +{ +} + +void gdrom_device::device_start() +{ + save_item(NAME(read_type)); + save_item(NAME(data_select)); + save_item(NAME(transferOffset)); + + /// TODO: split identify buffer into another method as device_start() should be called after it's filled in, but the atapi_cdrom_device has it's own. + atapi_cdrom_device::device_start(); + + memset(m_identify_buffer, 0, sizeof(m_identify_buffer)); + + m_identify_buffer[0] = 0x8600; // ATAPI device, cmd set 6 compliant, DRQ within 3 ms of PACKET command + + m_identify_buffer[23] = ('S' << 8) | 'E'; + m_identify_buffer[24] = (' ' << 8) | ' '; + m_identify_buffer[25] = (' ' << 8) | ' '; + m_identify_buffer[26] = (' ' << 8) | ' '; + + m_identify_buffer[27] = ('C' << 8) | 'D'; + m_identify_buffer[28] = ('-' << 8) | 'R'; + m_identify_buffer[29] = ('O' << 8) | 'M'; + m_identify_buffer[30] = (' ' << 8) | 'D'; + m_identify_buffer[31] = ('R' << 8) | 'I'; + m_identify_buffer[32] = ('V' << 8) | 'E'; + m_identify_buffer[33] = (' ' << 8) | ' '; + m_identify_buffer[34] = (' ' << 8) | ' '; + m_identify_buffer[35] = ('6' << 8) | '.'; + m_identify_buffer[36] = ('4' << 8) | '2'; + m_identify_buffer[37] = (' ' << 8) | ' '; + m_identify_buffer[38] = (' ' << 8) | ' '; + m_identify_buffer[39] = (' ' << 8) | ' '; + m_identify_buffer[40] = (' ' << 8) | ' '; + m_identify_buffer[41] = (' ' << 8) | ' '; + m_identify_buffer[42] = (' ' << 8) | ' '; + m_identify_buffer[43] = (' ' << 8) | ' '; + m_identify_buffer[44] = (' ' << 8) | ' '; + m_identify_buffer[45] = (' ' << 8) | ' '; + m_identify_buffer[46] = (' ' << 8) | ' '; + + m_identify_buffer[49] = 0x0400; // IORDY may be disabled + + m_identify_buffer[63]=7; // multi word dma mode 0-2 supported + m_identify_buffer[64]=1; // PIO mode 3 supported +} + +void gdrom_device::process_buffer() +{ + atapi_hle_device::process_buffer(); + // HACK: find out when this should be updated + m_sector_number = 0x80 | GDROM_PAUSE_STATE; +} + +void gdrom_device::signature() +{ + atapi_hle_device::signature(); + + // naomi dimm board firmware needs the upper nibble to be 8 at the beginning + if (is_real_gdrom_disc) + m_sector_number = 0x81; +} diff --git a/src/devices/bus/ata/gdrom.h b/src/devices/bus/ata/gdrom.h new file mode 100644 index 00000000000..66565e7160b --- /dev/null +++ b/src/devices/bus/ata/gdrom.h @@ -0,0 +1,46 @@ +// license:BSD-3-Clause +// copyright-holders:smf, Angelo Salese +/*************************************************************************** + + gdrom.h + +***************************************************************************/ + +#ifndef MAME_BUS_ATA_GDROM_H +#define MAME_BUS_ATA_GDROM_H + +#pragma once + +#include "atapicdr.h" + +class gdrom_device : public atapi_cdrom_device +{ +public: + gdrom_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + + // Sega GD-ROM handler + + virtual void ExecCommand() override; + virtual void WriteData( uint8_t *data, int dataLength ) override; + virtual void ReadData( uint8_t *data, int dataLength ) override; + +protected: + virtual void process_buffer() override; + virtual void signature() override; + virtual void SetDevice(void *device) override; + + // device-level overrides + virtual void device_start() override; + virtual void device_reset() override; + +private: + uint8_t GDROM_Cmd11_Reply[32]; + uint32_t read_type = 0; // for command 0x30 only + uint32_t data_select = 0; // for command 0x30 only + uint32_t transferOffset = 0; + bool is_real_gdrom_disc; +}; + +DECLARE_DEVICE_TYPE(GDROM, gdrom_device) + +#endif // MAME_BUS_ATA_GDROM_H diff --git a/src/devices/cpu/z80/mc8123.cpp b/src/devices/cpu/z80/mc8123.cpp new file mode 100644 index 00000000000..33acc77b096 --- /dev/null +++ b/src/devices/cpu/z80/mc8123.cpp @@ -0,0 +1,416 @@ +// license:BSD-3-Clause +// copyright-holders:Nicola Salmoria, David Widel +/*************************************************************************** + +NEC MC-8123 encryption emulation + +Decryption tables provided by David Widel +Decryption algorithm by Nicola Salmoria + +The NEC MC-8123 is a Z80 with built-in encryption. +It contains 0x2000 bytes of battery-backed RAM, when the battery dies the +game stops working. It's possible that the CPU would work as a normal Z80 +in that case, this hasn't been verified. + +When the CPU reads a byte from memory, it uses 12 bits of the address and +the information of whether the byte is an opcode or not to select a byte in +the internal RAM. The byte controls how the decryption works. + +A special value in the internal RAM instructs the CPU to not apply the decryption +algorithm at all. This is necessary for the CPU to be able to use RAM areas +normally. + +In theory, the size of the key would make the encryption quite secure. + +In practice, the contents of the internal RAM were generated using a linear +congruential generator, so the whole key can be generated starting from a single +24-bit seed. + +The LCG is the same that was used to generate the FD1094 keys. +Note that the algorithm skips the special value that would instruct the CPU to +not decrypt at that address. + +void generate_key(uint8_t (&key)[0x2000], uint32_t seed, unsigned upper_bound) +{ + unsigned i; + + for (i = 0; i < upper_bound; ++i) + { + uint8_t byteval; + + do + { + seed *= 0x29; + seed += seed << 16; + + byteval = (~seed >> 16) & 0xff; + } + while (byteval == 0xff); + + key[i] = byteval; + } + + for ( ; i < 0x2000; ++i) + key[i] = 0xff; +} + + +The known games that use this CPU are: + +CPU # Game Notes Seed Upper Limit +-------- ------------------------- ------------------ ------ ----- +317-0029 Block Gal NEC MC-8123B 651 091755 1800? +317-0030 Perfect Billiard 9451EC 1C00 +317-0040 Toki no Senshi - Chrono Soldier 068713 1c00 +317-0042 Opa Opa B31FD0 1C00 +317-0043 Wonder Boy Monster Land 640708 1C00 +317-0054 Shinobi (sound CPU) NEC MC-8123B 652 088992 1800 +317-0057 Fantasy Zone 2 ADFACE 1800 +317-0064 Ufo Senshi Yohko Chan 880603 1C00 +317-0066 Altered Beast (sound CPU) NEC MC-8123B 704 ED8600 1800 +317-5002 Gigas 1 & 2 NEC MC-8123 638 234567 1C00 +317-5004 Eagle Writer Not Dumped +317-5005 Astro Flash Not Dumped +317-5008 Perfect Billiard 9451EC 1C00 +317-5012 Ganbare Chinsan Ooshoubu NEC MC-8123A 804B54 1C00 +317-5014 DakkoChan Jansoh NEC MC-8123B 206850 1C00 +317-5??? Ninja Kid II (sound CPU) NEC MC-8123A 646 27998D 1800 +317-???? Center Court (sound CPU) NEC MC-8123B 703 640506 1800 +317-???? Omega 861226 1C00? + +***************************************************************************/ + +#include "emu.h" +#include "mc8123.h" + + +DEFINE_DEVICE_TYPE(MC8123, mc8123_device, "mc8123", "MC-8123") + +//------------------------------------------------- +// mc8123_device - constructor +//------------------------------------------------- + +mc8123_device::mc8123_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : z80_device(mconfig, MC8123, tag, owner, clock) + , m_key(*this, "key") +{ +} + + +namespace { + +template constexpr u8 BITS(T b) { return u8(1) << b; } +template constexpr u8 BITS(T b, U... c) { return (u8(1) << b) | BITS(c...); } + +} // anonymous namespace + +u8 mc8123_device::decrypt_type0(u8 val, u8 param, unsigned swap) +{ + if (swap == 0) val = bitswap<8>(val,7,5,3,1,2,0,6,4); + if (swap == 1) val = bitswap<8>(val,5,3,7,2,1,0,4,6); + if (swap == 2) val = bitswap<8>(val,0,3,4,6,7,1,5,2); + if (swap == 3) val = bitswap<8>(val,0,7,3,2,6,4,1,5); + + if (BIT(param,3) && BIT(val,7)) + val ^= BITS(5,3,0); + + if (BIT(param,2) && BIT(val,6)) + val ^= BITS(7,2,1); + + if (BIT(val,6)) val ^= BITS(7); + + if (BIT(param,1) && BIT(val,7)) + val ^= BITS(6); + + if (BIT(val,2)) val ^= BITS(5,0); + + val ^= BITS(4,3,1); + + if (BIT(param,2)) val ^= BITS(5,2,0); + if (BIT(param,1)) val ^= BITS(7,6); + if (BIT(param,0)) val ^= BITS(5,0); + + if (BIT(param,0)) val = bitswap<8>(val,7,6,5,1,4,3,2,0); + + return val; +} + + +u8 mc8123_device::decrypt_type1a(u8 val, u8 param, unsigned swap) +{ + if (swap == 0) val = bitswap<8>(val,4,2,6,5,3,7,1,0); + if (swap == 1) val = bitswap<8>(val,6,0,5,4,3,2,1,7); + if (swap == 2) val = bitswap<8>(val,2,3,6,1,4,0,7,5); + if (swap == 3) val = bitswap<8>(val,6,5,1,3,2,7,0,4); + + if (BIT(param,2)) val = bitswap<8>(val,7,6,1,5,3,2,4,0); + + if (BIT(val,1)) val ^= BITS(0); + if (BIT(val,6)) val ^= BITS(3); + if (BIT(val,7)) val ^= BITS(6,3); + if (BIT(val,2)) val ^= BITS(6,3,1); + if (BIT(val,4)) val ^= BITS(7,6,2); + + if (BIT(val,7) ^ BIT(val,2)) + val ^= BITS(4); + + val ^= BITS(6,3,1,0); + + if (BIT(param,3)) val ^= BITS(7,2); + if (BIT(param,1)) val ^= BITS(6,3); + + if (BIT(param,0)) val = bitswap<8>(val,7,6,1,4,3,2,5,0); + + return val; +} + +u8 mc8123_device::decrypt_type1b(u8 val, u8 param, unsigned swap) +{ + if (swap == 0) val = bitswap<8>(val,1,0,3,2,5,6,4,7); + if (swap == 1) val = bitswap<8>(val,2,0,5,1,7,4,6,3); + if (swap == 2) val = bitswap<8>(val,6,4,7,2,0,5,1,3); + if (swap == 3) val = bitswap<8>(val,7,1,3,6,0,2,5,4); + + if (BIT(val,2) && BIT(val,0)) + val ^= BITS(7,4); + + if (BIT(val,7)) val ^= BITS(2); + if (BIT(val,5)) val ^= BITS(7,2); + if (BIT(val,1)) val ^= BITS(5); + if (BIT(val,6)) val ^= BITS(1); + if (BIT(val,4)) val ^= BITS(6,5); + if (BIT(val,0)) val ^= BITS(6,2,1); + if (BIT(val,3)) val ^= BITS(7,6,2,1,0); + + val ^= BITS(6,4,0); + + if (BIT(param,3)) val ^= BITS(4,1); + if (BIT(param,2)) val ^= BITS(7,6,3,0); + if (BIT(param,1)) val ^= BITS(4,3); + if (BIT(param,0)) val ^= BITS(6,2,1,0); + + return val; +} + +u8 mc8123_device::decrypt_type2a(u8 val, u8 param, unsigned swap) +{ + if (swap == 0) val = bitswap<8>(val,0,1,4,3,5,6,2,7); + if (swap == 1) val = bitswap<8>(val,6,3,0,5,7,4,1,2); + if (swap == 2) val = bitswap<8>(val,1,6,4,5,0,3,7,2); + if (swap == 3) val = bitswap<8>(val,4,6,7,5,2,3,1,0); + + if (BIT(val,3) || (BIT(param,1) && BIT(val,2))) + val = bitswap<8>(val,6,0,7,4,3,2,1,5); + + if (BIT(val,5)) val ^= BITS(7); + if (BIT(val,6)) val ^= BITS(5); + if (BIT(val,0)) val ^= BITS(6); + if (BIT(val,4)) val ^= BITS(3,0); + if (BIT(val,1)) val ^= BITS(2); + + val ^= BITS(7,6,5,4,1); + + if (BIT(param,2)) val ^= BITS(4,3,2,1,0); + + if (BIT(param,3)) + { + if (BIT(param,0)) + val = bitswap<8>(val,7,6,5,3,4,1,2,0); + else + val = bitswap<8>(val,7,6,5,1,2,4,3,0); + } + else if (BIT(param,0)) + { + val = bitswap<8>(val,7,6,5,2,1,3,4,0); + } + + return val; +} + +u8 mc8123_device::decrypt_type2b(u8 val, u8 param, unsigned swap) +{ + // only 0x20 possible encryptions for this method - all others have 0x40 + // this happens because BIT(param,2) cancels the other three + + if (swap == 0) val = bitswap<8>(val,1,3,4,6,5,7,0,2); + if (swap == 1) val = bitswap<8>(val,0,1,5,4,7,3,2,6); + if (swap == 2) val = bitswap<8>(val,3,5,4,1,6,2,0,7); + if (swap == 3) val = bitswap<8>(val,5,2,3,0,4,7,6,1); + + if (BIT(val,7) && BIT(val,3)) + val ^= BITS(6,4,0); + + if (BIT(val,7)) val ^= BITS(2); + if (BIT(val,5)) val ^= BITS(7,3); + if (BIT(val,1)) val ^= BITS(5); + if (BIT(val,4)) val ^= BITS(7,5,3,1); + + if (BIT(val,7) && BIT(val,5)) + val ^= BITS(4,0); + + if (BIT(val,5) && BIT(val,1)) + val ^= BITS(4,0); + + if (BIT(val,6)) val ^= BITS(7,5); + if (BIT(val,3)) val ^= BITS(7,6,5,1); + if (BIT(val,2)) val ^= BITS(3,1); + + val ^= BITS(7,3,2,1); + + if (BIT(param,3)) val ^= BITS(6,3,1); + if (BIT(param,2)) val ^= BITS(7,6,5,3,2,1); // same as the other three combined + if (BIT(param,1)) val ^= BITS(7); + if (BIT(param,0)) val ^= BITS(5,2); + + return val; +} + +u8 mc8123_device::decrypt_type3a(u8 val, u8 param, unsigned swap) +{ + if (swap == 0) val = bitswap<8>(val,5,3,1,7,0,2,6,4); + if (swap == 1) val = bitswap<8>(val,3,1,2,5,4,7,0,6); + if (swap == 2) val = bitswap<8>(val,5,6,1,2,7,0,4,3); + if (swap == 3) val = bitswap<8>(val,5,6,7,0,4,2,1,3); + + if (BIT(val,2)) val ^= BITS(7,5,4); + if (BIT(val,3)) val ^= BITS(0); + + if (BIT(param,0)) val = bitswap<8>(val,7,2,5,4,3,1,0,6); + + if (BIT(val,1)) val ^= BITS(6,0); + if (BIT(val,3)) val ^= BITS(4,2,1); + + if (BIT(param,3)) val ^= BITS(4,3); + + if (BIT(val,3)) val = bitswap<8>(val,5,6,7,4,3,2,1,0); + + if (BIT(val,5)) val ^= BITS(2,1); + + val ^= BITS(6,5,4,3); + + if (BIT(param,2)) val ^= BITS(7); + if (BIT(param,1)) val ^= BITS(4); + if (BIT(param,0)) val ^= BITS(0); + + return val; +} + +u8 mc8123_device::decrypt_type3b(u8 val, u8 param, unsigned swap) +{ + if (swap == 0) val = bitswap<8>(val,3,7,5,4,0,6,2,1); + if (swap == 1) val = bitswap<8>(val,7,5,4,6,1,2,0,3); + if (swap == 2) val = bitswap<8>(val,7,4,3,0,5,1,6,2); + if (swap == 3) val = bitswap<8>(val,2,6,4,1,3,7,0,5); + + if (BIT(val,2)) val ^= BITS(7); + + if (BIT(val,7)) val = bitswap<8>(val,7,6,3,4,5,2,1,0); + + if (BIT(param,3)) val ^= BITS(7); + + if (BIT(val,4)) val ^= BITS(6); + if (BIT(val,1)) val ^= BITS(6,4,2); + + if (BIT(val,7) && BIT(val,6)) + val ^= BITS(1); + + if (BIT(val,7)) val ^= BITS(1); + + if (BIT(param,3)) val ^= BITS(7); + if (BIT(param,2)) val ^= BITS(0); + + if (BIT(param,3)) val = bitswap<8>(val,4,6,3,2,5,0,1,7); + + if (BIT(val,4)) val ^= BITS(1); + if (BIT(val,5)) val ^= BITS(4); + if (BIT(val,7)) val ^= BITS(2); + + val ^= BITS(5,3,2); + + if (BIT(param,1)) val ^= BITS(7); + if (BIT(param,0)) val ^= BITS(3); + + return val; +} + +u8 mc8123_device::decrypt_internal(u8 val, u8 key, bool opcode) +{ + unsigned type = 0; + unsigned swap = 0; + u8 param = 0; + + key ^= 0xff; + + // no encryption + if (key == 0x00) + return val; + + type ^= BIT(key,0) << 0; + type ^= BIT(key,2) << 0; + type ^= BIT(key,0) << 1; + type ^= BIT(key,1) << 1; + type ^= BIT(key,2) << 1; + type ^= BIT(key,4) << 1; + type ^= BIT(key,4) << 2; + type ^= BIT(key,5) << 2; + + swap ^= BIT(key,0) << 0; + swap ^= BIT(key,1) << 0; + swap ^= BIT(key,2) << 1; + swap ^= BIT(key,3) << 1; + + param ^= BIT(key,0) << 0; + param ^= BIT(key,0) << 1; + param ^= BIT(key,2) << 1; + param ^= BIT(key,3) << 1; + param ^= BIT(key,0) << 2; + param ^= BIT(key,1) << 2; + param ^= BIT(key,6) << 2; + param ^= BIT(key,1) << 3; + param ^= BIT(key,6) << 3; + param ^= BIT(key,7) << 3; + + if (!opcode) + { + param ^= BITS(0); + type ^= BITS(0); + } + + switch (type) + { + default: + case 0: return decrypt_type0(val, param, swap); + case 1: return decrypt_type0(val, param, swap); + case 2: return decrypt_type1a(val, param, swap); + case 3: return decrypt_type1b(val, param, swap); + case 4: return decrypt_type2a(val, param, swap); + case 5: return decrypt_type2b(val, param, swap); + case 6: return decrypt_type3a(val, param, swap); + case 7: return decrypt_type3b(val, param, swap); + } +} + + +u8 mc8123_device::decrypt(offs_t addr, u8 val, bool opcode) +{ + // pick the translation table from bits fd57 of the address + offs_t const tbl_num = bitswap<12>(addr,15,14,13,12,11,10,8,6,4,2,1,0); + + return decrypt_internal(val, m_key[tbl_num | (opcode ? 0x0000 : 0x1000)], opcode); +} + + +void mc8123_device::decode(u8 *rom, u8 *opcodes, unsigned length) +{ + for (unsigned i = 0; i < length; i++) + { + unsigned const adr = (i >= 0xc000) ? ((i & 0x3fff) | 0x8000) : i; + u8 const src = rom[i]; + + // decode the opcodes + opcodes[i] = decrypt(adr, src, true); + + // decode the data + rom[i] = decrypt(adr, src, false); + } +} diff --git a/src/devices/cpu/z80/mc8123.h b/src/devices/cpu/z80/mc8123.h new file mode 100644 index 00000000000..8fad72dbee7 --- /dev/null +++ b/src/devices/cpu/z80/mc8123.h @@ -0,0 +1,43 @@ +// license:BSD-3-Clause +// copyright-holders:Nicola Salmoria, David Widel +/*************************************************************************** + + NEC MC-8123 encryption emulation + +***************************************************************************/ + +#ifndef MAME_CPU_Z80_MC8123_H +#define MAME_CPU_Z80_MC8123_H + +#pragma once + +#include "z80.h" + +class mc8123_device : public z80_device +{ +public: + // construction/destruction + mc8123_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); + + // this function assumes a fixed portion of ROM at 0000-7FFF, and + // an arbitrary amount of banks at 8000-BFFF. + void decode(u8 *rom, u8 *opcodes, unsigned length); + +private: + static u8 decrypt_type0(u8 val, u8 param, unsigned swap); + static u8 decrypt_type1a(u8 val, u8 param, unsigned swap); + static u8 decrypt_type1b(u8 val, u8 param, unsigned swap); + static u8 decrypt_type2a(u8 val, u8 param, unsigned swap); + static u8 decrypt_type2b(u8 val, u8 param, unsigned swap); + static u8 decrypt_type3a(u8 val, u8 param, unsigned swap); + static u8 decrypt_type3b(u8 val, u8 param, unsigned swap); + static u8 decrypt_internal(u8 val, u8 key, bool opcode); + + u8 decrypt(offs_t addr, u8 val, bool opcode); + + required_region_ptr m_key; +}; + +DECLARE_DEVICE_TYPE(MC8123, mc8123_device) + +#endif // MAME_CPU_Z80_MC8123_H diff --git a/src/devices/machine/bacta_datalogger.cpp b/src/devices/machine/bacta_datalogger.cpp new file mode 100644 index 00000000000..43f9855bfd9 --- /dev/null +++ b/src/devices/machine/bacta_datalogger.cpp @@ -0,0 +1,218 @@ +// license:BSD-3-Clause +// copyright-holders:James Wallace +#include "emu.h" +#include "bacta_datalogger.h" + +#define LOG_DATA (1U << 1) + +//#define VERBOSE (LOG_DATA) +//#define LOG_OUTPUT_STREAM std::cout + +#include "logmacro.h" + +#define LOGDATA(...) LOGMASKED(LOG_DATA, __VA_ARGS__) + +/*********************************************************************************************************** + BACTA Datalogger emulation + The British Amusement and Catering Trade Association created a standard for the tracking of statistics + and other features on British AWPs across hardware manufacturers. + The specification is very simple, a 1200 Baud null modem connection via RS232, with the logger sending an + ACK command (0x06) on receipt of a valid character, and NAK (0x15) on error. + In this emulation, the simplest possible device is simulated here, derived from the RS232 null_modem. + We only handle the feedback for acknowledgment, and limited logging. +************************************************************************************************************/ + +// device type definition +DEFINE_DEVICE_TYPE(BACTA_DATALOGGER, bacta_datalogger_device, "bacta_datalogger", "BACTA Datalogger") + +//------------------------------------------------- +// bacta_datalogger_device - constructor +//------------------------------------------------- + +bacta_datalogger_device::bacta_datalogger_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : + bacta_datalogger_device(mconfig, BACTA_DATALOGGER, tag, owner, clock) +{ +} + +bacta_datalogger_device::bacta_datalogger_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock) : + device_t(mconfig, BACTA_DATALOGGER, tag, owner, clock), + device_serial_interface(mconfig, *this), + m_rxd_handler(*this), + m_last_input(-1), + m_output_char(0) +{ +} + +void bacta_datalogger_device::device_start() +{ + m_rxd_handler.resolve_safe(); +} + +void bacta_datalogger_device::device_reset() +{ + int startbits = 1; + int databits = 8; + parity_t parity = device_serial_interface::PARITY_ODD; + stop_bits_t stopbits = device_serial_interface::STOP_BITS_1; + + set_data_frame(startbits, databits, parity, stopbits); + + set_tra_rate(1200); + + set_rcv_rate(1200); + + output_rxd(1); +} + +void bacta_datalogger_device::tx_queue() +{ + if (is_transmit_register_empty()) + { + if (m_output_char != 255) + { + set_tra_rate(1200); + transmit_register_setup(m_output_char); + m_output_char = 255; + } + } +} + +void bacta_datalogger_device::tra_callback() +{ + output_rxd(transmit_register_get_data_bit()); +} + +void bacta_datalogger_device::tra_complete() +{ + // Shut down transmitter until there's a character + set_tra_rate(attotime::never); + tx_queue(); +} + +void bacta_datalogger_device::rcv_complete() +{ + u8 data; + + receive_register_extract(); + + data = get_received_char(); + if (data != 0x00) + { + if (data > 0x80) + { + data &= ~0x80; + if ( data == m_last_input) + { + LOGDATA("Retransmission of %x\n",data); + } + m_last_input = data; + } + switch (data) + { + case 0x01: + LOGDATA("(%c) Prize 1 vend or 0x01\n",data); + break; + case 0x02: + LOGDATA("(%c) Prize 2 vend or 0x02\n",data); + break; + case 0x03: + LOGDATA("(%c) Prize 3 vend or 0x03\n",data); + break; + case 0x04: + LOGDATA("(%c) Prize 4 vend or 0x04\n",data); + break; + case 0x05: + LOGDATA("(%c) Remote Credit or 0x05\n",data); + break; + case 0x07: + LOGDATA("(%c) Idle or 0x07\n",data); + break; + case 0x08: + LOGDATA("(%c) Change or 0x08\n",data); + break; + case 0x09: + case 0x0a: + case 0x0b: + case 0x0c: + case 0x0d: + case 0x0e: + case 0x0f: + LOGDATA("(%c) User defined message or 0x0%x\n",data,data); + break; + case 0x2b: + LOGDATA("(%c) Cashbox door open 0x2b\n",data); + break; + case 0x2c: + LOGDATA("(%c) Cashbox door closed 0x2c\n",data); + break; + case 0x2d: + LOGDATA("(%c) Service door open 0x2d\n",data); + break; + case 0x2e: + LOGDATA("(%c) Service door closed 0x2e\n",data); + break; + case 0x60: + LOGDATA("(%c) Primary message (0x%x), next byte is message length\n",data,data); + break; + case 0x61: + LOGDATA("(%c) Coin Tube / Hopper Levels 0x61 \n",data); + break; + case 0x62: + LOGDATA("(%c) Secondary message (0x%x), next byte is message length\n",data,data); + break; + case 0x63: + LOGDATA("(%c) Critical Fault 0x63\n",data); + break; + case 0x64: + LOGDATA("(%c) Non Critical Fault 0x64\n",data); + break; + case 0x65: + LOGDATA("(%c) Manufacturer Message Header 0x65, next byte is message length\n",data); + break; + case 0x66: + LOGDATA("(%c) Potential Parameter Data request 0x66, not currently supported\n",data); + break; + case 0x67: + LOGDATA("(%c) Potential Parameter Report request 0x67, not currently supported\n",data); + break; + case 0x68: + LOGDATA("(%c) Multi-Stake Multi-Game message 0x68\n",data); + break; + case 0x69: + LOGDATA("(%c) Cashless source 0x69\n",data); + break; + case 0x70: + case 0x71: + case 0x72: + case 0x73: + case 0x74: + case 0x75: + case 0x76: + case 0x77: + case 0x78: + case 0x79: + case 0x7a: + case 0x7b: + case 0x7c: + case 0x7d: + case 0x7e: + case 0x7f: + LOGDATA("(%c) User defined message (0x%x), next byte is message length\n",data,data); + break; + + default: + LOGDATA("(%c) Received: %02x\n",data, data); + break; + } + m_output_char = 0x06;//ACK + tx_queue(); + } + else + { + if (data != 0x00) + { + m_output_char = 0x15;//NAK + tx_queue(); + } + } +} diff --git a/src/devices/machine/bacta_datalogger.h b/src/devices/machine/bacta_datalogger.h new file mode 100644 index 00000000000..61555d85acd --- /dev/null +++ b/src/devices/machine/bacta_datalogger.h @@ -0,0 +1,39 @@ +// license:BSD-3-Clause +// copyright-holders:James Wallace +#ifndef MAME_MACHINE_BACTA_DATALOGGER_H +#define MAME_MACHINE_BACTA_DATALOGGER_H + +#include "diserial.h" + +class bacta_datalogger_device : public device_t, + public device_serial_interface +{ +public: + bacta_datalogger_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock = 0); + + virtual WRITE_LINE_MEMBER( write_txd ) {device_serial_interface::rx_w(state); } + auto rxd_handler() { return m_rxd_handler.bind(); } + + DECLARE_WRITE_LINE_MEMBER( output_rxd ) { m_rxd_handler(state); } + +protected: + bacta_datalogger_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock); + + virtual void device_start() override; + virtual void device_reset() override; + + virtual void tra_callback() override; + virtual void tra_complete() override; + virtual void rcv_complete() override; + +private: + void tx_queue(); + + devcb_write_line m_rxd_handler; + uint8_t m_last_input; + uint8_t m_output_char; +}; + +DECLARE_DEVICE_TYPE(BACTA_DATALOGGER, bacta_datalogger_device) + +#endif // MAME_MACHINE_BACTA_DATALOGGER_H diff --git a/src/devices/machine/nmk112.cpp b/src/devices/machine/nmk112.cpp new file mode 100644 index 00000000000..4de5062ac14 --- /dev/null +++ b/src/devices/machine/nmk112.cpp @@ -0,0 +1,103 @@ +// license:BSD-3-Clause +// copyright-holders:Alex W. Jackson +/* NMK112 - NMK custom IC for bankswitching the sample ROMs of a pair of + OKI6295 ADPCM chips + + The address space of each OKI6295 is divided into four banks, each one + independently controlled. The sample table at the beginning of the + address space may be divided in four pages as well, banked together + with the sample data. This allows each of the four voices on the chip + to play a sample from a different bank at the same time. */ + +#include "emu.h" +#include "nmk112.h" + +#define TABLESIZE 0x100 +#define BANKSIZE 0x10000 + + + +DEFINE_DEVICE_TYPE(NMK112, nmk112_device, "nmk112", "NMK112") + +nmk112_device::nmk112_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) + : device_t(mconfig, NMK112, tag, owner, clock) + , m_page_mask(0xff) + , m_rom0(*this, finder_base::DUMMY_TAG) + , m_rom1(*this, finder_base::DUMMY_TAG) + , m_size0(0) + , m_size1(0) +{ +} + +//------------------------------------------------- +// device_start - device-specific startup +//------------------------------------------------- + +void nmk112_device::device_start() +{ + save_item(NAME(m_current_bank)); + + if (m_rom0) + m_size0 = m_rom0.bytes() - 0x40000; + + if (m_rom1) + m_size1 = m_rom1.bytes() - 0x40000; +} + +//------------------------------------------------- +// device_reset - device-specific reset +//------------------------------------------------- + +void nmk112_device::device_reset() +{ + for (int i = 0; i < 8; i++) + { + m_current_bank[i] = 0; + do_bankswitch(i, m_current_bank[i]); + } +} + +void nmk112_device::do_bankswitch( int offset, int data ) +{ + int chip = (offset & 4) >> 2; + int banknum = offset & 3; + int paged = (m_page_mask & (1 << chip)); + + uint8_t *rom = chip ? m_rom1 : m_rom0; + int size = chip ? m_size1 : m_size0; + + m_current_bank[offset] = data; + + if (size == 0) return; + + int bankaddr = (data * BANKSIZE) % size; + + /* copy the samples */ + if ((paged) && (banknum == 0)) + memcpy(rom + 0x400, rom + 0x40000 + bankaddr + 0x400, BANKSIZE - 0x400); + else + memcpy(rom + banknum * BANKSIZE, rom + 0x40000 + bankaddr, BANKSIZE); + + /* also copy the sample address table, if it is paged on this chip */ + if (paged) + { + rom += banknum * TABLESIZE; + memcpy(rom, rom + 0x40000 + bankaddr, TABLESIZE); + } +} + +/***************************************************************************** + DEVICE HANDLERS +*****************************************************************************/ + +void nmk112_device::okibank_w(offs_t offset, u8 data) +{ + if (m_current_bank[offset] != data) + do_bankswitch(offset, data); +} + +void nmk112_device::device_post_load() +{ + for (int i = 0; i < 8; i++) + do_bankswitch(i, m_current_bank[i]); +} diff --git a/src/devices/machine/nmk112.h b/src/devices/machine/nmk112.h new file mode 100644 index 00000000000..5535d94899b --- /dev/null +++ b/src/devices/machine/nmk112.h @@ -0,0 +1,53 @@ +// license:BSD-3-Clause +// copyright-holders:Alex W. Jackson +/************************************************************************* + + nmk112.h + +**************************************************************************/ + +#ifndef MAME_MACHINE_NMK112_H +#define MAME_MACHINE_NMK112_H + +#pragma once + +/*************************************************************************** + TYPE DEFINITIONS +***************************************************************************/ + +class nmk112_device : public device_t +{ +public: + nmk112_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + + // configuration + template nmk112_device &set_rom0_tag(T &&tag) { m_rom0.set_tag(std::forward(tag)); return *this; } + template nmk112_device &set_rom1_tag(T &&tag) { m_rom1.set_tag(std::forward(tag)); return *this; } + nmk112_device &set_page_mask(uint8_t mask) { m_page_mask = ~mask; return *this; } + + void okibank_w(offs_t offset, u8 data); + +protected: + // device-level overrides + virtual void device_start() override; + virtual void device_reset() override; + virtual void device_post_load() override; + +private: + void do_bankswitch( int offset, int data ); + + // internal state + + /* which chips have their sample address table divided into pages */ + uint8_t m_page_mask; + + uint8_t m_current_bank[8]; + + optional_region_ptr m_rom0, m_rom1; + int m_size0, m_size1; +}; + +DECLARE_DEVICE_TYPE(NMK112, nmk112_device) + + +#endif // MAME_MACHINE_NMK112_H diff --git a/src/devices/video/k051316.cpp b/src/devices/video/k051316.cpp new file mode 100644 index 00000000000..5f59e3f8b83 --- /dev/null +++ b/src/devices/video/k051316.cpp @@ -0,0 +1,304 @@ +// license:BSD-3-Clause +// copyright-holders:Fabio Priuli,Acho A. Tang, R. Belmont +/* +Konami 051316 PSAC +------ +Manages a 32x32 tilemap (16x16 tiles, 512x512 pixels) which can be zoomed, +distorted and rotated. +It uses two internal 24 bit counters which are incremented while scanning the +picture. The coordinates of the pixel in the tilemap that has to be drawn to +the current beam position are the counters / (2^11). +The chip doesn't directly generate the color information for the pixel, it +just generates a 24 bit address (whose top 16 bits are the contents of the +tilemap RAM), and a "visible" signal. It's up to external circuitry to convert +the address into a pixel color. Most games seem to use 4bpp graphics, but Ajax +uses 7bpp. +If the value in the internal counters is out of the visible range (0..511), it +is truncated and the corresponding address is still generated, but the "visible" +signal is not asserted. The external circuitry might ignore that signal and +still generate the pixel, therefore making the tilemap a continuous playfield +that wraps around instead of a large sprite. + +control registers +000-001 X counter starting value / 256 +002-003 amount to add to the X counter after each horizontal pixel +004-005 amount to add to the X counter after each line (0 = no rotation) +006-007 Y counter starting value / 256 +008-009 amount to add to the Y counter after each horizontal pixel (0 = no rotation) +00a-00b amount to add to the Y counter after each line +00c-00d ROM bank to read, used during ROM testing +00e bit 0 = enable ROM reading (active low). This only makes the chip output the + requested address: the ROM is actually read externally, not through + the chip's data bus. + bit 1 = unknown + bit 2 = unknown +00f unused + +*/ + +#include "emu.h" +#include "k051316.h" + + +#define VERBOSE 0 +#include "logmacro.h" + + +DEFINE_DEVICE_TYPE(K051316, k051316_device, "k051316", "K051316 PSAC") + + +const gfx_layout k051316_device::charlayout4 = +{ + 16,16, + RGN_FRAC(1,1), + 4, + { 0, 1, 2, 3 }, + { 0*4, 1*4, 2*4, 3*4, 4*4, 5*4, 6*4, 7*4, + 8*4, 9*4, 10*4, 11*4, 12*4, 13*4, 14*4, 15*4 }, + { 0*64, 1*64, 2*64, 3*64, 4*64, 5*64, 6*64, 7*64, + 8*64, 9*64, 10*64, 11*64, 12*64, 13*64, 14*64, 15*64 }, + 128*8 +}; + +const gfx_layout k051316_device::charlayout7 = +{ + 16,16, + RGN_FRAC(1,1), + 7, + { 1,2,3,4,5,6,7 }, + { 0*8, 1*8, 2*8, 3*8, 4*8, 5*8, 6*8, 7*8, + 8*8, 9*8, 10*8, 11*8, 12*8, 13*8, 14*8, 15*8 }, + { 0*128, 1*128, 2*128, 3*128, 4*128, 5*128, 6*128, 7*128, + 8*128, 9*128, 10*128, 11*128, 12*128, 13*128, 14*128, 15*128 }, + 256*8 +}; + +const gfx_layout k051316_device::charlayout8 = +{ + 16,16, + RGN_FRAC(1,1), + 8, + { 0,1,2,3,4,5,6,7 }, + { 0*8, 1*8, 2*8, 3*8, 4*8, 5*8, 6*8, 7*8, + 8*8, 9*8, 10*8, 11*8, 12*8, 13*8, 14*8, 15*8 }, + { 0*128, 1*128, 2*128, 3*128, 4*128, 5*128, 6*128, 7*128, + 8*128, 9*128, 10*128, 11*128, 12*128, 13*128, 14*128, 15*128 }, + 256*8 +}; + + +GFXDECODE_MEMBER( k051316_device::gfxinfo ) + GFXDECODE_DEVICE(DEVICE_SELF, 0, charlayout4, 0, 1) +GFXDECODE_END + +GFXDECODE_MEMBER( k051316_device::gfxinfo7 ) + GFXDECODE_DEVICE(DEVICE_SELF, 0, charlayout7, 0, 1) +GFXDECODE_END + +GFXDECODE_MEMBER( k051316_device::gfxinfo8 ) + GFXDECODE_DEVICE(DEVICE_SELF, 0, charlayout8, 0, 1) +GFXDECODE_END + +GFXDECODE_MEMBER( k051316_device::gfxinfo4_ram ) + GFXDECODE_DEVICE_RAM(DEVICE_SELF, 0, charlayout4, 0, 1) +GFXDECODE_END + + +k051316_device::k051316_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) + : device_t(mconfig, K051316, tag, owner, clock) + , device_gfx_interface(mconfig, *this, gfxinfo) + , m_zoom_rom(*this, DEVICE_SELF) + , m_dx(0) + , m_dy(0) + , m_wrap(0) + , m_pixels_per_byte(2) // 4bpp layout is default + , m_layermask(0) + , m_k051316_cb(*this) +{ +} + +void k051316_device::set_bpp(int bpp) +{ + switch(bpp) + { + case 4: + set_info(gfxinfo); + m_pixels_per_byte = 2; + break; + case 7: + set_info(gfxinfo7); + m_pixels_per_byte = 1; + break; + case 8: + set_info(gfxinfo8); + m_pixels_per_byte = 1; + break; + case -4: + set_info(gfxinfo4_ram); + m_pixels_per_byte = 2; + break; + default: + fatalerror("Unsupported bpp\n"); + } +} + + + +//------------------------------------------------- +// device_start - device-specific startup +//------------------------------------------------- + +void k051316_device::device_start() +{ + // assumes it can make an address mask with .length() - 1 + assert(!(m_zoom_rom.length() & (m_zoom_rom.length() - 1))); + + if (!palette().device().started()) + throw device_missing_dependencies(); + + // bind callbacks + m_k051316_cb.resolve(); + + decode_gfx(); + gfx(0)->set_colors(palette().entries() / gfx(0)->depth()); + + m_tmap = &machine().tilemap().create(*this, tilemap_get_info_delegate(*this, FUNC(k051316_device::get_tile_info)), TILEMAP_SCAN_ROWS, 16, 16, 32, 32); + m_ram.resize(0x800); + memset(&m_ram[0], 0, 0x800); + + if (m_layermask) + { + m_tmap->map_pens_to_layer(0, 0, 0, TILEMAP_PIXEL_LAYER1); + m_tmap->map_pens_to_layer(0, m_layermask, m_layermask, TILEMAP_PIXEL_LAYER0); + } + else + m_tmap->set_transparent_pen(0); + + save_item(NAME(m_ram)); + save_item(NAME(m_ctrlram)); + save_item(NAME(m_wrap)); + +} + +//------------------------------------------------- +// device_reset - device-specific reset +//------------------------------------------------- + +void k051316_device::device_reset() +{ + memset(m_ctrlram, 0, 0x10); +} + +/***************************************************************************** + DEVICE HANDLERS +*****************************************************************************/ + +u8 k051316_device::read(offs_t offset) +{ + return m_ram[offset]; +} + +void k051316_device::write(offs_t offset, u8 data) +{ + m_ram[offset] = data; + m_tmap->mark_tile_dirty(offset & 0x3ff); +} + + +u8 k051316_device::rom_r(offs_t offset) +{ + assert (m_zoom_rom.found()); + + if ((m_ctrlram[0x0e] & 0x01) == 0) + { + int addr = offset + (m_ctrlram[0x0c] << 11) + (m_ctrlram[0x0d] << 19); + addr /= m_pixels_per_byte; + addr &= m_zoom_rom.length() - 1; + + // popmessage("%s: offset %04x addr %04x", machine().describe_context(), offset, addr); + + return m_zoom_rom[addr]; + } + else + { + //logerror("%s: read 051316 ROM offset %04x but reg 0x0c bit 0 not clear\n", machine().describe_context(), offset); + return 0; + } +} + +void k051316_device::ctrl_w(offs_t offset, u8 data) +{ + m_ctrlram[offset] = data; + //if (offset >= 0x0c) logerror("%s: write %02x to 051316 reg %x\n", machine().describe_context(), data, offset); +} + +// some games (ajax, rollerg, ultraman, etc.) have external logic that can enable or disable wraparound dynamically +void k051316_device::wraparound_enable( int status ) +{ + m_wrap = status; +} + +/*************************************************************************** + + Callbacks for the TileMap code + +***************************************************************************/ + +TILE_GET_INFO_MEMBER(k051316_device::get_tile_info) +{ + int code = m_ram[tile_index]; + int color = m_ram[tile_index + 0x400]; + int flags = 0; + + m_k051316_cb(&code, &color, &flags); + + tileinfo.set(0, + code, + color, + flags); +} + + +void k051316_device::zoom_draw( screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, int flags, uint32_t priority ) +{ + uint32_t startx, starty; + int incxx, incxy, incyx, incyy; + + startx = 256 * ((int16_t)(256 * m_ctrlram[0x00] + m_ctrlram[0x01])); + incxx = (int16_t)(256 * m_ctrlram[0x02] + m_ctrlram[0x03]); + incyx = (int16_t)(256 * m_ctrlram[0x04] + m_ctrlram[0x05]); + starty = 256 * ((int16_t)(256 * m_ctrlram[0x06] + m_ctrlram[0x07])); + incxy = (int16_t)(256 * m_ctrlram[0x08] + m_ctrlram[0x09]); + incyy = (int16_t)(256 * m_ctrlram[0x0a] + m_ctrlram[0x0b]); + + startx -= (16 + m_dy) * incyx; + starty -= (16 + m_dy) * incyy; + + startx -= (89 + m_dx) * incxx; + starty -= (89 + m_dx) * incxy; + + m_tmap->draw_roz(screen, bitmap, cliprect, startx << 5, starty << 5, + incxx << 5, incxy << 5, incyx << 5, incyy << 5, + m_wrap, + flags, priority); + +#if 0 + popmessage("%02x%02x%02x%02x %02x%02x%02x%02x %02x%02x%02x%02x %02x%02x%02x%02x", + m_ctrlram[0x00], + m_ctrlram[0x01], + m_ctrlram[0x02], + m_ctrlram[0x03], + m_ctrlram[0x04], + m_ctrlram[0x05], + m_ctrlram[0x06], + m_ctrlram[0x07], + m_ctrlram[0x08], + m_ctrlram[0x09], + m_ctrlram[0x0a], + m_ctrlram[0x0b], + m_ctrlram[0x0c], /* bank for ROM testing */ + m_ctrlram[0x0d], + m_ctrlram[0x0e], /* 0 = test ROMs */ + m_ctrlram[0x0f]); +#endif +} diff --git a/src/devices/video/k051316.h b/src/devices/video/k051316.h new file mode 100644 index 00000000000..db3df893986 --- /dev/null +++ b/src/devices/video/k051316.h @@ -0,0 +1,86 @@ +// license:BSD-3-Clause +// copyright-holders:Fabio Priuli,Acho A. Tang, R. Belmont +#ifndef MAME_VIDEO_K051316_H +#define MAME_VIDEO_K051316_H + +#pragma once + +#include "tilemap.h" + + +#define K051316_CB_MEMBER(_name) void _name(int *code, int *color, int *flags) + + +class k051316_device : public device_t, public device_gfx_interface +{ +public: + using zoom_delegate = device_delegate; + + k051316_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + + static const gfx_layout charlayout4; + static const gfx_layout charlayout7; + static const gfx_layout charlayout8; + DECLARE_GFXDECODE_MEMBER(gfxinfo); + DECLARE_GFXDECODE_MEMBER(gfxinfo7); + DECLARE_GFXDECODE_MEMBER(gfxinfo8); + DECLARE_GFXDECODE_MEMBER(gfxinfo4_ram); + + // configuration + template void set_zoom_callback(T &&... args) { m_k051316_cb.set(std::forward(args)...); } + void set_wrap(int wrap) { m_wrap = wrap; } + void set_bpp(int bpp); + void set_layermask(int mask) { m_layermask = mask; } + void set_offsets(int x_offset, int y_offset) + { + m_dx = x_offset; + m_dy = y_offset; + } + + /* + The callback is passed: + - code (range 00-FF, contents of the first tilemap RAM byte) + - color (range 00-FF, contents of the first tilemap RAM byte). Note that bit 6 + seems to be hardcoded as flip X. + The callback must put: + - in code the resulting tile number + - in color the resulting color index + - if necessary, put flags for the TileMap code in the tile_info + structure (e.g. TILE_FLIPX) + */ + + u8 read(offs_t offset); + void write(offs_t offset, u8 data); + u8 rom_r(offs_t offset); + void ctrl_w(offs_t offset, u8 data); + void zoom_draw(screen_device &screen, bitmap_ind16 &bitmap,const rectangle &cliprect,int flags,uint32_t priority); + void wraparound_enable(int status); + + void mark_gfx_dirty(offs_t byteoffset) { gfx(0)->mark_dirty(byteoffset * m_pixels_per_byte / (16 * 16)); } + void mark_tmap_dirty() { m_tmap->mark_all_dirty(); } + +protected: + // device-level overrides + virtual void device_start() override; + virtual void device_reset() override; + +private: + // internal state + std::vector m_ram; + uint8_t m_ctrlram[16]; + tilemap_t *m_tmap = nullptr; + + optional_region_ptr m_zoom_rom; + + int m_dx, m_dy; + int m_wrap; + int m_pixels_per_byte; + int m_layermask; + zoom_delegate m_k051316_cb; + + TILE_GET_INFO_MEMBER(get_tile_info); +}; + +DECLARE_DEVICE_TYPE(K051316, k051316_device) + +#endif // MAME_VIDEO_K051316_H diff --git a/src/devices/video/k053936.cpp b/src/devices/video/k053936.cpp new file mode 100644 index 00000000000..c9900430b53 --- /dev/null +++ b/src/devices/video/k053936.cpp @@ -0,0 +1,855 @@ +// license:BSD-3-Clause +// copyright-holders:David Haywood +/* */ + +#include "emu.h" +#include "k053936.h" + +#define VERBOSE 0 +#include "logmacro.h" + + +// Localized K053936/ROZ+ +#define K053936_MAX_CHIPS 2 + +static rectangle K053936_cliprect[K053936_MAX_CHIPS]; +static int K053936_offset[K053936_MAX_CHIPS][2] = {{0,0},{0,0}}; +static int K053936_clip_enabled[K053936_MAX_CHIPS] = {0,0}; +static int K053936_wraparound[K053936_MAX_CHIPS]; + + + + +/***************************************************************************/ +/* */ +/* 053936 */ +/* */ +/***************************************************************************/ + +/* + +053936 +------ +Evolution of the 051316. The data bus is 16-bit instead of 8-bit. +When used in "simple" mode it can generate the same effects of the 051316, but it +doesn't have internal tilemap RAM, so it just generates a couple of X/Y coordinates +indicating the pixel to display at each moment. Therefore, the tilemap and tile +sizes are not fixed. +The important addition over the 051316 is 512x4 words of internal RAM used to control +rotation and zoom scanline by scanline instead that on the whole screen, allowing for +effects like linescroll (Super Slams) or 3D rotation of the tilemap (Golfing Greats, +Premier Soccer). + +control registers +000 X counter starting value / 256 +001 Y counter starting value / 256 +002 ["simple" mode only] amount to add to the X counter after each line (0 = no rotation) +003 ["simple" mode only] amount to add to the Y counter after each line +004 ["simple" mode only] amount to add to the X counter after each horizontal pixel +005 ["simple" mode only] amount to add to the Y counter after each horizontal pixel (0 = no rotation) +006 x------- -------- when set, register (line*4)+2 must be multiplied by 256 + -x------ -------- when set, registers 002 and 003 must be multiplied by 256 + --xxxxxx -------- clipping for the generated address? usually 3F, Premier Soccer + sets it to 07 before penalty kicks + -------- x------- when set, register (line*4)+3 must be multiplied by 256 + -------- -x------ when set, registers 004 and 005 must be multiplied by 256 + -------- --xxxxxx clipping for the generated address? usually 3F, Premier Soccer + sets it to 0F before penalty kicks +007 -------- -x------ enable "super" mode + -------- --x----- unknown (enable address clipping from register 006?) + -------- ---x---- unknown + -------- ------x- (not sure) enable clipping with registers 008-00b +008 min x screen coordinate to draw to (only when enabled by register 7) +009 max x screen coordinate to draw to (only when enabled by register 7) +00a min y screen coordinate to draw to (only when enabled by register 7) +00b max y screen coordinate to draw to (only when enabled by register 7) +00c unknown +00d unknown +00e unknown +00f unknown + +additional control from extra RAM: +(line*4)+0 X counter starting value / 256 (add to register 000) +(line*4)+1 Y counter starting value / 256 (add to register 001) +(line*4)+2 amount to add to the X counter after each horizontal pixel +(line*4)+3 amount to add to the Y counter after each horizontal pixel + +*/ + + + + +static void K053936_zoom_draw(int chip,uint16_t *ctrl,uint16_t *linectrl, screen_device &screen, bitmap_ind16 &bitmap,const rectangle &cliprect,tilemap_t *tmap,int flags,uint32_t priority, int glfgreat_hack) +{ + if (!tmap) + return; + + if (ctrl[0x07] & 0x0040) + { + uint32_t startx,starty; + int incxx,incxy; + rectangle my_clip; + int y,maxy; + + // Racin' Force will get to here if glfgreat_hack is enabled, and it ends + // up setting a maximum y value of '13', thus causing nothing to be drawn. + // It looks like the roz output should be flipped somehow as it seems to be + // displaying the wrong areas of the tilemap and is rendered upside down, + // although due to the additional post-processing the voxel renderer performs + // it's difficult to know what the output SHOULD be. (hold W in Racin' Force + // to see the chip output) + + if (((ctrl[0x07] & 0x0002) && ctrl[0x09]) && (glfgreat_hack)) /* wrong, but fixes glfgreat */ + { + my_clip.min_x = ctrl[0x08] + K053936_offset[chip][0]+2; + my_clip.max_x = ctrl[0x09] + K053936_offset[chip][0]+2 - 1; + if (my_clip.min_x < cliprect.min_x) + my_clip.min_x = cliprect.min_x; + if (my_clip.max_x > cliprect.max_x) + my_clip.max_x = cliprect.max_x; + + y = ctrl[0x0a] + K053936_offset[chip][1]-2; + if (y < cliprect.min_y) + y = cliprect.min_y; + maxy = ctrl[0x0b] + K053936_offset[chip][1]-2 - 1; + if (maxy > cliprect.max_y) + maxy = cliprect.max_y; + + } + else + { + my_clip.min_x = cliprect.min_x; + my_clip.max_x = cliprect.max_x; + + y = cliprect.min_y; + maxy = cliprect.max_y; + } + + while (y <= maxy) + { + uint16_t *lineaddr = linectrl + 4*((y - K053936_offset[chip][1]) & 0x1ff); + my_clip.min_y = my_clip.max_y = y; + + startx = 256 * (int16_t)(lineaddr[0] + ctrl[0x00]); + starty = 256 * (int16_t)(lineaddr[1] + ctrl[0x01]); + incxx = (int16_t)(lineaddr[2]); + incxy = (int16_t)(lineaddr[3]); + + if (ctrl[0x06] & 0x8000) incxx *= 256; + if (ctrl[0x06] & 0x0080) incxy *= 256; + + startx -= K053936_offset[chip][0] * incxx; + starty -= K053936_offset[chip][0] * incxy; + + tmap->draw_roz(screen, bitmap, my_clip, startx << 5,starty << 5, + incxx << 5,incxy << 5,0,0, + K053936_wraparound[chip], + flags,priority); + + y++; + } + } + else /* "simple" mode */ + { + uint32_t startx,starty; + int incxx,incxy,incyx,incyy; + + startx = 256 * (int16_t)(ctrl[0x00]); + starty = 256 * (int16_t)(ctrl[0x01]); + incyx = (int16_t)(ctrl[0x02]); + incyy = (int16_t)(ctrl[0x03]); + incxx = (int16_t)(ctrl[0x04]); + incxy = (int16_t)(ctrl[0x05]); + + if (ctrl[0x06] & 0x4000) { incyx *= 256; incyy *= 256; } + if (ctrl[0x06] & 0x0040) { incxx *= 256; incxy *= 256; } + + startx -= K053936_offset[chip][1] * incyx; + starty -= K053936_offset[chip][1] * incyy; + + startx -= K053936_offset[chip][0] * incxx; + starty -= K053936_offset[chip][0] * incxy; + + tmap->draw_roz(screen, bitmap, cliprect, startx << 5,starty << 5, + incxx << 5,incxy << 5,incyx << 5,incyy << 5, + K053936_wraparound[chip], + flags,priority); + } + +#if 0 +if (machine.input().code_pressed(KEYCODE_D)) + popmessage("%04x %04x %04x %04x\n%04x %04x %04x %04x\n%04x %04x %04x %04x\n%04x %04x %04x %04x", + ctrl[0x00], + ctrl[0x01], + ctrl[0x02], + ctrl[0x03], + ctrl[0x04], + ctrl[0x05], + ctrl[0x06], + ctrl[0x07], + ctrl[0x08], + ctrl[0x09], + ctrl[0x0a], + ctrl[0x0b], + ctrl[0x0c], + ctrl[0x0d], + ctrl[0x0e], + ctrl[0x0f]); +#endif +} + + +void K053936_0_zoom_draw(screen_device &screen, bitmap_ind16 &bitmap,const rectangle &cliprect,tilemap_t *tmap,int flags,uint32_t priority, int glfgreat_hack) +{ + uint16_t *ctrl = reinterpret_cast(tmap->machine().root_device().memshare("k053936_0_ctrl")->ptr()); + uint16_t *linectrl = reinterpret_cast(tmap->machine().root_device().memshare("k053936_0_line")->ptr()); + K053936_zoom_draw(0,ctrl,linectrl,screen,bitmap,cliprect,tmap,flags,priority, glfgreat_hack); +} + +void K053936_wraparound_enable(int chip, int status) +{ + K053936_wraparound[chip] = status; +} + + +void K053936_set_offset(int chip, int xoffs, int yoffs) +{ + K053936_offset[chip][0] = xoffs; + K053936_offset[chip][1] = yoffs; +} + + + + +/***************************************************************************/ +/* */ +/* 053936 */ +/* */ +/***************************************************************************/ + +DEFINE_DEVICE_TYPE(K053936, k053936_device, "k053936", "K053936 Video Controller") + +k053936_device::k053936_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) + : device_t(mconfig, K053936, tag, owner, clock), + m_ctrl(nullptr), + m_linectrl(nullptr), + m_wrap(0), + m_xoff(0), + m_yoff(0) +{ +} + +//------------------------------------------------- +// device_start - device-specific startup +//------------------------------------------------- + +void k053936_device::device_start() +{ + m_ctrl = make_unique_clear(0x20); + m_linectrl = make_unique_clear(0x4000); + + save_pointer(NAME(m_ctrl), 0x20); + save_pointer(NAME(m_linectrl), 0x4000); +} + +//------------------------------------------------- +// device_reset - device-specific reset +//------------------------------------------------- + +void k053936_device::device_reset() +{ + memset(m_ctrl.get(), 0, 0x20); +} + + +/***************************************************************************** + DEVICE HANDLERS +*****************************************************************************/ + +void k053936_device::ctrl_w(offs_t offset, uint16_t data, uint16_t mem_mask) +{ + COMBINE_DATA(&m_ctrl[offset]); +} + +uint16_t k053936_device::ctrl_r(offs_t offset) +{ + return m_ctrl[offset]; +} + +void k053936_device::linectrl_w(offs_t offset, uint16_t data, uint16_t mem_mask) +{ + COMBINE_DATA(&m_linectrl[offset]); +} + +uint16_t k053936_device::linectrl_r(offs_t offset) +{ + return m_linectrl[offset]; +} + +// there is another implementation of this in video/konamigx.c (!) +// why? shall they be merged? +void k053936_device::zoom_draw( screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int flags, uint32_t priority, int glfgreat_hack ) +{ + if (!tmap) + return; + + if (m_ctrl[0x07] & 0x0040) + { + uint32_t startx, starty; + int incxx, incxy; + rectangle my_clip; + int y, maxy; + + // Racin' Force will get to here if glfgreat_hack is enabled, and it ends + // up setting a maximum y value of '13', thus causing nothing to be drawn. + // It looks like the roz output should be flipped somehow as it seems to be + // displaying the wrong areas of the tilemap and is rendered upside down, + // although due to the additional post-processing the voxel renderer performs + // it's difficult to know what the output SHOULD be. (hold W in Racin' Force + // to see the chip output) + + if (((m_ctrl[0x07] & 0x0002) && m_ctrl[0x09]) && (glfgreat_hack)) /* wrong, but fixes glfgreat */ + { + my_clip.min_x = m_ctrl[0x08] + m_xoff + 2; + my_clip.max_x = m_ctrl[0x09] + m_xoff + 2 - 1; + if (my_clip.min_x < cliprect.min_x) + my_clip.min_x = cliprect.min_x; + if (my_clip.max_x > cliprect.max_x) + my_clip.max_x = cliprect.max_x; + + y = m_ctrl[0x0a] + m_yoff - 2; + if (y < cliprect.min_y) + y = cliprect.min_y; + maxy = m_ctrl[0x0b] + m_yoff - 2 - 1; + if (maxy > cliprect.max_y) + maxy = cliprect.max_y; + } + else + { + my_clip.min_x = cliprect.min_x; + my_clip.max_x = cliprect.max_x; + + y = cliprect.min_y; + maxy = cliprect.max_y; + } + + while (y <= maxy) + { + uint16_t *lineaddr = m_linectrl.get() + 4 * ((y - m_yoff) & 0x1ff); + + my_clip.min_y = my_clip.max_y = y; + + startx = 256 * (int16_t)(lineaddr[0] + m_ctrl[0x00]); + starty = 256 * (int16_t)(lineaddr[1] + m_ctrl[0x01]); + incxx = (int16_t)(lineaddr[2]); + incxy = (int16_t)(lineaddr[3]); + + if (m_ctrl[0x06] & 0x8000) + incxx *= 256; + + if (m_ctrl[0x06] & 0x0080) + incxy *= 256; + + startx -= m_xoff * incxx; + starty -= m_xoff * incxy; + + tmap->draw_roz(screen, bitmap, my_clip, startx << 5,starty << 5, + incxx << 5,incxy << 5,0,0, + m_wrap, + flags,priority); + + y++; + } + } + else /* "simple" mode */ + { + uint32_t startx, starty; + int incxx, incxy, incyx, incyy; + + startx = 256 * (int16_t)(m_ctrl[0x00]); + starty = 256 * (int16_t)(m_ctrl[0x01]); + incyx = (int16_t)(m_ctrl[0x02]); + incyy = (int16_t)(m_ctrl[0x03]); + incxx = (int16_t)(m_ctrl[0x04]); + incxy = (int16_t)(m_ctrl[0x05]); + + if (m_ctrl[0x06] & 0x4000) + { + incyx *= 256; + incyy *= 256; + } + + if (m_ctrl[0x06] & 0x0040) + { + incxx *= 256; + incxy *= 256; + } + + startx -= m_yoff * incyx; + starty -= m_yoff * incyy; + + startx -= m_xoff * incxx; + starty -= m_xoff * incxy; + + tmap->draw_roz(screen, bitmap, cliprect, startx << 5,starty << 5, + incxx << 5,incxy << 5,incyx << 5,incyy << 5, + m_wrap, + flags,priority); + } + +#if 0 +if (machine.input().code_pressed(KEYCODE_D)) + popmessage("%04x %04x %04x %04x\n%04x %04x %04x %04x\n%04x %04x %04x %04x\n%04x %04x %04x %04x", + m_ctrl[0x00], + m_ctrl[0x01], + m_ctrl[0x02], + m_ctrl[0x03], + m_ctrl[0x04], + m_ctrl[0x05], + m_ctrl[0x06], + m_ctrl[0x07], + m_ctrl[0x08], + m_ctrl[0x09], + m_ctrl[0x0a], + m_ctrl[0x0b], + m_ctrl[0x0c], + m_ctrl[0x0d], + m_ctrl[0x0e], + m_ctrl[0x0f]); +#endif +} + +void k053936_device::zoom_draw( screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int flags, uint32_t priority, int glfgreat_hack ) +{ + if (!tmap) + return; + + if (m_ctrl[0x07] & 0x0040) + { + uint32_t startx, starty; + int incxx, incxy; + rectangle my_clip; + int y, maxy; + + // Racin' Force will get to here if glfgreat_hack is enabled, and it ends + // up setting a maximum y value of '13', thus causing nothing to be drawn. + // It looks like the roz output should be flipped somehow as it seems to be + // displaying the wrong areas of the tilemap and is rendered upside down, + // although due to the additional post-processing the voxel renderer performs + // it's difficult to know what the output SHOULD be. (hold W in Racin' Force + // to see the chip output) + + if (((m_ctrl[0x07] & 0x0002) && m_ctrl[0x09]) && (glfgreat_hack)) /* wrong, but fixes glfgreat */ + { + my_clip.min_x = m_ctrl[0x08] + m_xoff + 2; + my_clip.max_x = m_ctrl[0x09] + m_xoff + 2 - 1; + if (my_clip.min_x < cliprect.min_x) + my_clip.min_x = cliprect.min_x; + if (my_clip.max_x > cliprect.max_x) + my_clip.max_x = cliprect.max_x; + + y = m_ctrl[0x0a] + m_yoff - 2; + if (y < cliprect.min_y) + y = cliprect.min_y; + maxy = m_ctrl[0x0b] + m_yoff - 2 - 1; + if (maxy > cliprect.max_y) + maxy = cliprect.max_y; + } + else + { + my_clip.min_x = cliprect.min_x; + my_clip.max_x = cliprect.max_x; + + y = cliprect.min_y; + maxy = cliprect.max_y; + } + + while (y <= maxy) + { + uint16_t *lineaddr = m_linectrl.get() + 4 * ((y - m_yoff) & 0x1ff); + + my_clip.min_y = my_clip.max_y = y; + + startx = 256 * (int16_t)(lineaddr[0] + m_ctrl[0x00]); + starty = 256 * (int16_t)(lineaddr[1] + m_ctrl[0x01]); + incxx = (int16_t)(lineaddr[2]); + incxy = (int16_t)(lineaddr[3]); + + if (m_ctrl[0x06] & 0x8000) + incxx *= 256; + + if (m_ctrl[0x06] & 0x0080) + incxy *= 256; + + startx -= m_xoff * incxx; + starty -= m_xoff * incxy; + + tmap->draw_roz(screen, bitmap, my_clip, startx << 5,starty << 5, + incxx << 5,incxy << 5,0,0, + m_wrap, + flags,priority); + + y++; + } + } + else /* "simple" mode */ + { + uint32_t startx, starty; + int incxx, incxy, incyx, incyy; + + startx = 256 * (int16_t)(m_ctrl[0x00]); + starty = 256 * (int16_t)(m_ctrl[0x01]); + incyx = (int16_t)(m_ctrl[0x02]); + incyy = (int16_t)(m_ctrl[0x03]); + incxx = (int16_t)(m_ctrl[0x04]); + incxy = (int16_t)(m_ctrl[0x05]); + + if (m_ctrl[0x06] & 0x4000) + { + incyx *= 256; + incyy *= 256; + } + + if (m_ctrl[0x06] & 0x0040) + { + incxx *= 256; + incxy *= 256; + } + + startx -= m_yoff * incyx; + starty -= m_yoff * incyy; + + startx -= m_xoff * incxx; + starty -= m_xoff * incxy; + + tmap->draw_roz(screen, bitmap, cliprect, startx << 5,starty << 5, + incxx << 5,incxy << 5,incyx << 5,incyy << 5, + m_wrap, + flags,priority); + } +} + + + + +void K053936GP_set_offset(int chip, int xoffs, int yoffs) { K053936_offset[chip][0] = xoffs; K053936_offset[chip][1] = yoffs; } + +void K053936GP_clip_enable(int chip, int status) { K053936_clip_enabled[chip] = status; } + +void K053936GP_set_cliprect(int chip, int minx, int maxx, int miny, int maxy) +{ + rectangle &cliprect = K053936_cliprect[chip]; + cliprect.set(minx, maxx, miny, maxy); +} + +static inline void K053936GP_copyroz32clip( running_machine &machine, + bitmap_rgb32 &dst_bitmap, bitmap_ind16 &src_bitmap, + const rectangle &dst_cliprect, const rectangle &src_cliprect, + uint32_t _startx,uint32_t _starty,int _incxx,int _incxy,int _incyx,int _incyy, + int tilebpp, int blend, int alpha, int clip, int pixeldouble_output, palette_device &palette ) +{ + static const int colormask[8]={1,3,7,0xf,0x1f,0x3f,0x7f,0xff}; + int cy, cx; + int ecx; + int src_pitch, incxy, incxx; + int src_minx, src_maxx, src_miny, src_maxy, cmask; + uint16_t *src_base; + size_t src_size; + + const pen_t *pal_base; + int dst_ptr; + int dst_size; + int dst_base2; + + int tx, dst_pitch; + uint32_t *dst_base; + int starty, incyy, startx, incyx, ty, sx, sy; + + incxy = _incxy; incxx = _incxx; incyy = _incyy; incyx = _incyx; + starty = _starty; startx = _startx; + + if (clip) // set source clip range to some extreme values when disabled + { + src_minx = src_cliprect.min_x; + src_maxx = src_cliprect.max_x; + src_miny = src_cliprect.min_y; + src_maxy = src_cliprect.max_y; + } + // this simply isn't safe to do! + else { src_minx = src_miny = -0x10000; src_maxx = src_maxy = 0x10000; } + + // set target clip range + sx = dst_cliprect.min_x; + tx = dst_cliprect.max_x - sx + 1; + sy = dst_cliprect.min_y; + ty = dst_cliprect.max_y - sy + 1; + + startx += sx * incxx + sy * incyx; + starty += sx * incxy + sy * incyy; + + // adjust entry points and other loop constants + dst_pitch = dst_bitmap.rowpixels(); + dst_base = &dst_bitmap.pix(0); + dst_base2 = sy * dst_pitch + sx + tx; + ecx = tx = -tx; + + tilebpp = (tilebpp-1) & 7; + pal_base = palette.pens(); + cmask = colormask[tilebpp]; + + src_pitch = src_bitmap.rowpixels(); + src_base = &src_bitmap.pix(0); + src_size = src_bitmap.width() * src_bitmap.height(); + dst_size = dst_bitmap.width() * dst_bitmap.height(); + dst_ptr = 0;//dst_base; + cy = starty; + cx = startx; + + if (blend > 0) + { + dst_ptr += dst_pitch; // draw blended + starty += incyy; + startx += incyx; + + do { + do { + int srcx = (cx >> 16) & 0x1fff; + int srcy = (cy >> 16) & 0x1fff; + int pixel; + uint32_t offs; + offs = srcy * src_pitch + srcx; + + cx += incxx; + cy += incxy; + + if (offs>=src_size) + continue; + + if (srcx < src_minx || srcx > src_maxx || srcy < src_miny || srcy > src_maxy) + continue; + + pixel = src_base[offs]; + if (!(pixel & cmask)) + continue; + + if ((dst_ptr+ecx+dst_base2)> 16) & 0x1fff; + int srcy = (cy >> 16) & 0x1fff; + int pixel; + uint32_t offs; + + offs = srcy * src_pitch + srcx; + + cx += incxx; + cy += incxy; + + if (offs>=src_size) + continue; + + if (srcx < src_minx || srcx > src_maxx || srcy < src_miny || srcy > src_maxy) + continue; + + pixel = src_base[offs]; + if (!(pixel & cmask)) + continue; + + + + if ((dst_ptr+ecx+dst_base2)pixmap(); + rectangle &src_cliprect = K053936_cliprect[chip]; + clip = K053936_clip_enabled[chip]; + + if (ctrl[0x07] & 0x0040) /* "super" mode */ + { + my_clip.min_x = cliprect.min_x; + my_clip.max_x = cliprect.max_x; + y = cliprect.min_y; + maxy = cliprect.max_y; + + while (y <= maxy) + { + lineaddr = linectrl + ( ((y - K053936_offset[chip][1]) & 0x1ff) << 2); + my_clip.min_y = my_clip.max_y = y; + + startx = (int16_t)(lineaddr[0] + ctrl[0x00]) << 8; + starty = (int16_t)(lineaddr[1] + ctrl[0x01]) << 8; + incxx = (int16_t)(lineaddr[2]); + incxy = (int16_t)(lineaddr[3]); + + if (ctrl[0x06] & 0x8000) incxx <<= 8; + if (ctrl[0x06] & 0x0080) incxy <<= 8; + + startx -= K053936_offset[chip][0] * incxx; + starty -= K053936_offset[chip][0] * incxy; + + K053936GP_copyroz32clip(machine, + bitmap, src_bitmap, my_clip, src_cliprect, + startx<<5, starty<<5, incxx<<5, incxy<<5, 0, 0, + tilebpp, blend, alpha, clip, pixeldouble_output, palette); + y++; + } + } + else /* "simple" mode */ + { + startx = (int16_t)(ctrl[0x00]) << 8; + starty = (int16_t)(ctrl[0x01]) << 8; + incyx = (int16_t)(ctrl[0x02]); + incyy = (int16_t)(ctrl[0x03]); + incxx = (int16_t)(ctrl[0x04]); + incxy = (int16_t)(ctrl[0x05]); + + if (ctrl[0x06] & 0x4000) { incyx <<= 8; incyy <<= 8; } + if (ctrl[0x06] & 0x0040) { incxx <<= 8; incxy <<= 8; } + + startx -= K053936_offset[chip][1] * incyx; + starty -= K053936_offset[chip][1] * incyy; + + startx -= K053936_offset[chip][0] * incxx; + starty -= K053936_offset[chip][0] * incxy; + + K053936GP_copyroz32clip(machine, + bitmap, src_bitmap, cliprect, src_cliprect, + startx<<5, starty<<5, incxx<<5, incxy<<5, incyx<<5, incyy<<5, + tilebpp, blend, alpha, clip, pixeldouble_output, palette); + } +} + +static void K053936GP_zoom_draw(running_machine &machine, + int chip, uint32_t *ctrl1, uint32_t *linectrl1, + bitmap_rgb32 &bitmap, const rectangle &cliprect, tilemap_t *tmap, + int tilebpp, int blend, int alpha, int pixeldouble_output, palette_device &palette) +{ + uint16_t *lineaddr; + + // Horrible but that's what the code previously did, only hidden + uint16_t *ctrl = (uint16_t *)ctrl1; + uint16_t *linectrl = (uint16_t *)linectrl1; + + rectangle my_clip; + uint32_t startx, starty; + int incxx, incxy, incyx, incyy, y, maxy, clip; + + bitmap_ind16 &src_bitmap = tmap->pixmap(); + rectangle &src_cliprect = K053936_cliprect[chip]; + clip = K053936_clip_enabled[chip]; + + if (ctrl[0x07] & 0x0040) /* "super" mode */ + { + my_clip.min_x = cliprect.min_x; + my_clip.max_x = cliprect.max_x; + y = cliprect.min_y; + maxy = cliprect.max_y; + + while (y <= maxy) + { + lineaddr = linectrl + ( ((y - K053936_offset[chip][1]) & 0x1ff) << 2); + my_clip.min_y = my_clip.max_y = y; + + startx = (int16_t)(lineaddr[0] + ctrl[0x00]) << 8; + starty = (int16_t)(lineaddr[1] + ctrl[0x01]) << 8; + incxx = (int16_t)(lineaddr[2]); + incxy = (int16_t)(lineaddr[3]); + + if (ctrl[0x06] & 0x8000) incxx <<= 8; + if (ctrl[0x06] & 0x0080) incxy <<= 8; + + startx -= K053936_offset[chip][0] * incxx; + starty -= K053936_offset[chip][0] * incxy; + + K053936GP_copyroz32clip(machine, + bitmap, src_bitmap, my_clip, src_cliprect, + startx<<5, starty<<5, incxx<<5, incxy<<5, 0, 0, + tilebpp, blend, alpha, clip, pixeldouble_output, palette); + y++; + } + } + else /* "simple" mode */ + { + startx = (int16_t)(ctrl[0x00]) << 8; + starty = (int16_t)(ctrl[0x01]) << 8; + incyx = (int16_t)(ctrl[0x02]); + incyy = (int16_t)(ctrl[0x03]); + incxx = (int16_t)(ctrl[0x04]); + incxy = (int16_t)(ctrl[0x05]); + + if (ctrl[0x06] & 0x4000) { incyx <<= 8; incyy <<= 8; } + if (ctrl[0x06] & 0x0040) { incxx <<= 8; incxy <<= 8; } + + startx -= K053936_offset[chip][1] * incyx; + starty -= K053936_offset[chip][1] * incyy; + + startx -= K053936_offset[chip][0] * incxx; + starty -= K053936_offset[chip][0] * incxy; + + K053936GP_copyroz32clip(machine, + bitmap, src_bitmap, cliprect, src_cliprect, + startx<<5, starty<<5, incxx<<5, incxy<<5, incyx<<5, incyy<<5, + tilebpp, blend, alpha, clip, pixeldouble_output, palette); + } +} + +void K053936GP_0_zoom_draw(running_machine &machine, bitmap_rgb32 &bitmap, const rectangle &cliprect, + tilemap_t *tmap, int tilebpp, int blend, int alpha, int pixeldouble_output, uint16_t* temp_m_k053936_0_ctrl_16, uint16_t* temp_m_k053936_0_linectrl_16,uint32_t* temp_m_k053936_0_ctrl, uint32_t* temp_m_k053936_0_linectrl, palette_device &palette) +{ + if (temp_m_k053936_0_ctrl_16) + { + K053936GP_zoom_draw(machine, 0,temp_m_k053936_0_ctrl_16,temp_m_k053936_0_linectrl_16,bitmap,cliprect,tmap,tilebpp,blend,alpha, pixeldouble_output, palette); + } + else + { + K053936GP_zoom_draw(machine, 0,temp_m_k053936_0_ctrl,temp_m_k053936_0_linectrl,bitmap,cliprect,tmap,tilebpp,blend,alpha, pixeldouble_output, palette); + } +} diff --git a/src/devices/video/k053936.h b/src/devices/video/k053936.h new file mode 100644 index 00000000000..75894c2bf95 --- /dev/null +++ b/src/devices/video/k053936.h @@ -0,0 +1,60 @@ +// license:BSD-3-Clause +// copyright-holders:David Haywood +#ifndef MAME_VIDEO_K053936_H +#define MAME_VIDEO_K053936_H + +#pragma once + +#include "emupal.h" +#include "tilemap.h" + + +void K053936_0_zoom_draw(screen_device &screen, bitmap_ind16 &bitmap,const rectangle &cliprect,tilemap_t *tmap,int flags,uint32_t priority, int glfgreat_hack); +void K053936_wraparound_enable(int chip, int status); +void K053936_set_offset(int chip, int xoffs, int yoffs); + +// GX specific implementations... +void K053936GP_set_offset(int chip, int xoffs, int yoffs); +void K053936GP_clip_enable(int chip, int status); +void K053936GP_set_cliprect(int chip, int minx, int maxx, int miny, int maxy); +void K053936GP_0_zoom_draw(running_machine &machine, bitmap_rgb32 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int tilebpp, int blend, int alpha, int pixeldouble_output, uint16_t* temp_m_k053936_0_ctrl_16, uint16_t* temp_m_k053936_0_linectrl_16, uint32_t* temp_m_k053936_0_ctrl, uint32_t* temp_m_k053936_0_linectrl, palette_device &palette); + + +class k053936_device : public device_t +{ +public: + k053936_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + ~k053936_device() {} + + // configuration + void set_wrap(int wrap) { m_wrap = wrap; } + void set_offsets(int x_offset, int y_offset) + { + m_xoff = x_offset; + m_yoff = y_offset; + } + + void ctrl_w(offs_t offset, uint16_t data, uint16_t mem_mask = ~0); + uint16_t ctrl_r(offs_t offset); + void linectrl_w(offs_t offset, uint16_t data, uint16_t mem_mask = ~0); + uint16_t linectrl_r(offs_t offset); + void zoom_draw(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int flags, uint32_t priority, int glfgreat_hack); + void zoom_draw(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int flags, uint32_t priority, int glfgreat_hack); + // void wraparound_enable(int status); unused? // shall we merge this into the configuration intf? + // void set_offset(int xoffs, int yoffs); unused? // shall we merge this into the configuration intf? + +protected: + // device-level overrides + virtual void device_start() override; + virtual void device_reset() override; + +private: + // internal state + std::unique_ptr m_ctrl; + std::unique_ptr m_linectrl; + int m_wrap, m_xoff, m_yoff; +}; + +DECLARE_DEVICE_TYPE(K053936, k053936_device) + +#endif // MAME_VIDEO_K053936_H diff --git a/src/devices/video/tmap038.cpp b/src/devices/video/tmap038.cpp new file mode 100644 index 00000000000..9b007e28a2c --- /dev/null +++ b/src/devices/video/tmap038.cpp @@ -0,0 +1,263 @@ +// license:BSD-3-Clause +// copyright-holders:Luca Elia, Paul Priest, David Haywood +/* 038 Tilemap generator manufactured by NEC */ + +/* + [ Scrolling Layers ] + + Each 038 chip generates 1 layer. Up to 4 chips are used + (4 layers) + + Layer Size: 512 x 512 + Tiles: 8 x 8 & 16 x 16. + + There are 2 tilemaps in memory, one per tiles dimension. + A bit decides which one gets displayed. + The tiles depth varies with games, from 16 to 256 colors. + + A per layer row-scroll / row-select effect can be enabled: + + a different scroll value is fetched (from tile RAM) for each + scan line, and a different tilemap line for each scan line + + + +*************************************************************************** + + Callbacks for the TileMap code + + [ Tiles Format ] + + Offset: Bits: Value: + + 0.w fe-- ---- ---- --- Priority + --dc ba98 ---- ---- Color + ---- ---- 7654 3210 + + 2.w Code + + + When a row-scroll / row-select effect is enabled, the scroll values are + fetched starting from tile RAM + $1000, 4 bytes per scan line: + + Offset: Value: + + 0.w Tilemap line to display + 2.w X Scroll value + +*************************************************************************** + +*************************************************************************** + + Layers Registers + + + Offset: Bits: Value: + + 0.w f--- ---- ---- ---- 0 = Layer Flip X + -e-- ---- ---- ---- Activate Row-scroll + --d- ---- ---- ---- + ---c ba9- ---- ---- + ---- ---8 7654 3210 Scroll X + + 2.w f--- ---- ---- ---- 0 = Layer Flip Y + -e-- ---- ---- ---- Activate Row-select + --d- ---- ---- ---- 0 = 8x8 tiles, 1 = 16x16 tiles + ---c ba9- ---- ---- + ---- ---8 7654 3210 Scroll Y + + 4.w fedc ba98 765- ---- + ---- ---- ---4 ---- Layer Disable + ---- ---- ---- 3210 Varies* + + *color bank for mcatadv or Layer-Layer priority for cave + +There are more! + +*************************************************************************** + +TODO: + de-fragmentation and merge drawing behavior into tmap038.cpp + +*************************************************************************** + +*/ + +#include "emu.h" +#include "tmap038.h" + +void tilemap038_device::vram_map(address_map &map) +{ + map(0x0000, 0x0fff).rw(FUNC(tilemap038_device::vram_16x16_r), FUNC(tilemap038_device::vram_16x16_w)).share("vram_16x16"); + map(0x1000, 0x17ff).rw(FUNC(tilemap038_device::lineram_r), FUNC(tilemap038_device::lineram_w)).share("lineram"); + map(0x1800, 0x3fff).ram().share("scratchpad"); // scratchpad? + map(0x4000, 0x7fff).rw(FUNC(tilemap038_device::vram_8x8_r), FUNC(tilemap038_device::vram_8x8_w)).share("vram_8x8"); +} + +void tilemap038_device::vram_writeonly_map(address_map &map) +{ + map(0x0000, 0x0fff).w(FUNC(tilemap038_device::vram_16x16_w)).share("vram_16x16"); + map(0x1000, 0x17ff).w(FUNC(tilemap038_device::lineram_w)).share("lineram"); + map(0x1800, 0x3fff).writeonly().share("scratchpad"); // scratchpad? + map(0x4000, 0x7fff).w(FUNC(tilemap038_device::vram_8x8_w)).share("vram_8x8"); +} + +void tilemap038_device::vram_16x16_map(address_map &map) +{ + map(0x0000, 0x0fff).rw(FUNC(tilemap038_device::vram_16x16_r), FUNC(tilemap038_device::vram_16x16_w)).share("vram_16x16"); + map(0x1000, 0x17ff).rw(FUNC(tilemap038_device::lineram_r), FUNC(tilemap038_device::lineram_w)).share("lineram"); + map(0x1800, 0x3fff).ram().share("scratchpad"); // scratchpad? +} + +void tilemap038_device::vram_16x16_writeonly_map(address_map &map) +{ + map(0x0000, 0x0fff).w(FUNC(tilemap038_device::vram_16x16_w)).share("vram_16x16"); + map(0x1000, 0x17ff).w(FUNC(tilemap038_device::lineram_w)).share("lineram"); + map(0x1800, 0x3fff).writeonly().share("scratchpad"); // scratchpad? +} + +/* Some games, that only ever use the 8x8 tiles and no line scroll, + use mirror ram. For example in donpachi, writes to 400000-403fff + and 408000-407fff both go to the 8x8 tilemap ram. Use this function + in this cases. Note that the get_tile_info function looks in the + 4000-7fff range for tiles, so we have to write the data there. */ +void tilemap038_device::vram_8x8_map(address_map &map) +{ + map(0x0000, 0x3fff).rw(FUNC(tilemap038_device::vram_8x8_r), FUNC(tilemap038_device::vram_8x8_w)).share("vram_8x8"); +} + +DEFINE_DEVICE_TYPE(TMAP038, tilemap038_device, "tmap038", "038 Tilemap generator") + +tilemap038_device::tilemap038_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : device_t(mconfig, TMAP038, tag, owner, clock) + , m_vram_8x8(*this, "vram_8x8") + , m_vram_16x16(*this, "vram_16x16") + , m_lineram(*this, "lineram") + , m_vregs(nullptr) + , m_tiledim(false) + , m_gfxdecode(*this, finder_base::DUMMY_TAG) + , m_gfxno(0) + , m_038_cb(*this) + , m_xoffs(0) + , m_flipped_xoffs(0) + , m_yoffs(0) + , m_flipped_yoffs(0) +{ +} + +TILE_GET_INFO_MEMBER(tilemap038_device::get_tile_info) +{ + u32 tile, code = 0, color = 0, pri = 0; + + if (tile_is_16x16()) + { + tile = (tile_index % (512 / 8)) / 2 + ((tile_index / (512 / 8)) / 2) * (512 / 16); + tile = (m_vram_16x16 != nullptr) ? ((m_vram_16x16[tile * 2] << 16) + m_vram_16x16[(tile * 2) + 1]) : 0; + + color = (tile & 0x3f000000) >> (32 - 8); + pri = (tile & 0xc0000000) >> (32 - 2); + code = (tile & 0x0000ffff) * 4; + + code ^= tile_index & 1; + code ^= ((tile_index / (512 / 8)) & 1) * 2; + + if (!m_038_cb.isnull()) + m_038_cb(true, color, pri, code); + } + else if (tile_is_8x8()) + { + tile = (m_vram_8x8 != nullptr) ? ((m_vram_8x8[tile_index * 2] << 16) + m_vram_8x8[(tile_index * 2) + 1]) : 0; + + color = (tile & 0x3f000000) >> (32 - 8); + pri = (tile & 0xc0000000) >> (32 - 2); + code = (tile & 0x0003ffff); + + if (!m_038_cb.isnull()) + m_038_cb(false, color, pri, code); + } + + tileinfo.set(m_gfxno, code, color, 0); + tileinfo.category = pri; +} + + +void tilemap038_device::device_start() +{ + m_038_cb.resolve(); + m_vregs = make_unique_clear(0x6/2); + + if (m_vram_16x16 == nullptr && m_vram_8x8 == nullptr) + fatalerror("Tilemap 038 %s: VRAM not found",this->tag()); + + m_tmap = &machine().tilemap().create( + *m_gfxdecode, + tilemap_get_info_delegate(*this, FUNC(tilemap038_device::get_tile_info)), + TILEMAP_SCAN_ROWS, + 8,8, 512 / 8,512 / 8); + + m_tmap->set_transparent_pen(0); + + set_scroll_rows(1); // Initialize scroll rows + set_scroll_cols(1); // Initialize scroll cols + + save_item(NAME(m_tiledim)); + save_pointer(NAME(m_vregs), 0x6/2); +} + +void tilemap038_device::device_reset() +{ +} + +u16 tilemap038_device::vram_8x8_r(offs_t offset) +{ + return m_vram_8x8[offset]; +} + +void tilemap038_device::vram_8x8_w(offs_t offset, u16 data, u16 mem_mask) +{ + COMBINE_DATA(&m_vram_8x8[offset]); + if (tile_is_8x8()) + m_tmap->mark_tile_dirty(offset >> 1); +} + +u16 tilemap038_device::vram_16x16_r(offs_t offset) +{ + return m_vram_16x16[offset]; +} + +void tilemap038_device::vram_16x16_w(offs_t offset, u16 data, u16 mem_mask) +{ + COMBINE_DATA(&m_vram_16x16[offset]); + if (tile_is_16x16()) + { + offset >>= 1; + offset = (offset % (512 / 16)) * 2 + (offset / (512 / 16)) * (512 / 8) * 2; + m_tmap->mark_tile_dirty(offset + 0); + m_tmap->mark_tile_dirty(offset + 1); + m_tmap->mark_tile_dirty(offset + 0 + 512 / 8); + m_tmap->mark_tile_dirty(offset + 1 + 512 / 8); + } +} + +void tilemap038_device::prepare() +{ + // refresh tile size + if (m_vram_8x8 != nullptr && m_vram_16x16 != nullptr) + { + const bool new_tiledim = BIT(m_vregs[1], 13); + if (m_tiledim != new_tiledim) + { + m_tmap->mark_all_dirty(); + m_tiledim = new_tiledim; + } + } +} + +void tilemap038_device::draw(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, u32 flags, u8 pri, u8 pri_mask) { draw_common(screen, bitmap, cliprect, flags, pri, pri_mask); } +void tilemap038_device::draw(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect, u32 flags, u8 pri, u8 pri_mask) { draw_common(screen, bitmap, cliprect, flags, pri, pri_mask); } + +template +void tilemap038_device::draw_common(screen_device &screen, BitmapClass &bitmap, const rectangle &cliprect, u32 flags, u8 pri, u8 pri_mask) +{ + m_tmap->draw(screen, bitmap, cliprect, flags, pri, pri_mask); +} diff --git a/src/devices/video/tmap038.h b/src/devices/video/tmap038.h new file mode 100644 index 00000000000..cc5ba89813d --- /dev/null +++ b/src/devices/video/tmap038.h @@ -0,0 +1,114 @@ +// license:BSD-3-Clause +// copyright-holders:Luca Elia, Paul Priest, David Haywood +#ifndef MAME_VIDEO_TMAP038_H +#define MAME_VIDEO_TMAP038_H + +#pragma once + +#include "tilemap.h" + +class tilemap038_device : public device_t +{ +public: + typedef device_delegate tmap038_cb_delegate; + + tilemap038_device(const machine_config &mconfig, const char *tag, device_t *owner) + : tilemap038_device(mconfig, tag, owner, (u32)0) + { + } + + tilemap038_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); + + // configurations + template void set_gfxdecode_tag(T &&tag) { m_gfxdecode.set_tag(std::forward(tag)); } + template void set_tile_callback(T &&... args) { m_038_cb.set(std::forward(args)...); } + void set_gfx(u16 no) { m_gfxno = no; } + void set_xoffs(int xoffs, int flipped_xoffs) { m_xoffs = xoffs; m_flipped_xoffs = flipped_xoffs; } + void set_yoffs(int yoffs, int flipped_yoffs) { m_yoffs = yoffs; m_flipped_yoffs = flipped_yoffs; } + + // call to do the rendering etc. + template + void draw_common(screen_device &screen, BitmapClass &bitmap, const rectangle &cliprect, u32 flags, u8 pri = 0, u8 pri_mask = ~0); + + void prepare(); + void draw(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, u32 flags, u8 pri = 0, u8 pri_mask = ~0); + void draw(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect, u32 flags, u8 pri = 0, u8 pri_mask = ~0); + + // access + void vram_map(address_map &map); + void vram_8x8_map(address_map &map); + void vram_16x16_map(address_map &map); + + void vram_writeonly_map(address_map &map); + void vram_16x16_writeonly_map(address_map &map); + + u16 vram_8x8_r(offs_t offset); + void vram_8x8_w(offs_t offset, u16 data, u16 mem_mask); + + u16 vram_16x16_r(offs_t offset); + void vram_16x16_w(offs_t offset, u16 data, u16 mem_mask); + + u16 lineram_r(offs_t offset) { return m_lineram[offset]; } + void lineram_w(offs_t offset, u16 data, u16 mem_mask = ~0) { COMBINE_DATA(&m_lineram[offset]); } + + u16 vregs_r(offs_t offset) { return m_vregs[offset]; } + void vregs_w(offs_t offset, u16 data, u16 mem_mask = ~0) { COMBINE_DATA(&m_vregs[offset]); } + + void mark_all_dirty() { m_tmap->mark_all_dirty(); } + void set_flip(u32 attributes) { m_tmap->set_flip(attributes); } + void set_palette_offset(u32 offset) { m_tmap->set_palette_offset(offset); } + void set_scroll_rows(u32 scroll_rows) { m_tmap->set_scroll_rows(scroll_rows); } + void set_scroll_cols(u32 scroll_cols) { m_tmap->set_scroll_cols(scroll_cols); } + void set_scrollx(int which, int value) { m_tmap->set_scrollx(which, value); } + void set_scrolly(int which, int value) { m_tmap->set_scrolly(which, value); } + + // getters + u16 lineram(offs_t offset) const { return m_lineram[offset]; } + + u16 rowscroll(offs_t line) const { return rowscroll_en() ? m_lineram[((line & 0x1ff) * 2) + 0] : 0; } + u16 rowselect(offs_t line) const { return rowselect_en() ? m_lineram[((line & 0x1ff) * 2) + 1] : 0; } + + u16 vregs(offs_t offset) const { return m_vregs[offset]; } + + // vregs + bool flipx() const { return BIT(~m_vregs[0], 15); } + bool rowscroll_en() const { return BIT(m_vregs[0], 14) && (m_lineram != nullptr); } + int scrollx() const { return (m_vregs[0] & 0x1ff) + (flipx() ? m_flipped_xoffs : m_xoffs); } + + bool flipy() const { return BIT(~m_vregs[1], 15); } + bool rowselect_en() const { return BIT(m_vregs[1], 14) && (m_lineram != nullptr); } + bool tiledim() const { return m_tiledim; } + int scrolly() const { return (m_vregs[1] & 0x1ff) + (flipy() ? m_flipped_yoffs : m_yoffs); } + + bool enable() const { return BIT(~m_vregs[2], 4); } + u16 external() const { return m_vregs[2] & 0xf; } + + bool tile_is_8x8() const { return (!m_tiledim) || (m_vram_16x16 == nullptr); } + bool tile_is_16x16() const { return m_tiledim || (m_vram_8x8 == nullptr); } +protected: + virtual void device_start() override; + virtual void device_reset() override; + +private: + TILE_GET_INFO_MEMBER(get_tile_info); + optional_shared_ptr m_vram_8x8; + optional_shared_ptr m_vram_16x16; + optional_shared_ptr m_lineram; + std::unique_ptr m_vregs; + bool m_tiledim; + + // set when creating device + required_device m_gfxdecode; + u16 m_gfxno; + + tmap038_cb_delegate m_038_cb; + tilemap_t* m_tmap = nullptr; + + int m_xoffs, m_flipped_xoffs; + int m_yoffs, m_flipped_yoffs; +}; + + +DECLARE_DEVICE_TYPE(TMAP038, tilemap038_device) + +#endif // MAME_VIDEO_TMAP038_H diff --git a/src/mame/atlus/patapata.cpp b/src/mame/atlus/patapata.cpp index 5df02b7894a..8e188281ecb 100644 --- a/src/mame/atlus/patapata.cpp +++ b/src/mame/atlus/patapata.cpp @@ -18,9 +18,9 @@ maybe close to jalmah.cpp? */ #include "emu.h" -#include "nmk112.h" #include "cpu/m68000/m68000.h" +#include "machine/nmk112.h" #include "machine/timer.h" #include "sound/okim6295.h" diff --git a/src/mame/barcrest/mpu4.h b/src/mame/barcrest/mpu4.h index b6632ae7296..945345bd558 100644 --- a/src/mame/barcrest/mpu4.h +++ b/src/mame/barcrest/mpu4.h @@ -5,11 +5,10 @@ #include "mpu4_characteriser_pal.h" #include "mpu4_characteriser_pal_bwb.h" -#include "bacta_datalogger.h" - #include "cpu/m6809/m6809.h" #include "machine/6821pia.h" #include "machine/6840ptm.h" +#include "machine/bacta_datalogger.h" #include "machine/mc68681.h" #include "machine/meters.h" #include "machine/nvram.h" diff --git a/src/mame/bfm/rastersp.cpp b/src/mame/bfm/rastersp.cpp index ba4073bad5f..d412f6d3bd3 100644 --- a/src/mame/bfm/rastersp.cpp +++ b/src/mame/bfm/rastersp.cpp @@ -17,13 +17,13 @@ ****************************************************************************/ #include "emu.h" -#include "bacta_datalogger.h" #include "bus/nscsi/cd.h" #include "bus/nscsi/hd.h" #include "cpu/i386/i386.h" #include "cpu/tms32031/tms32031.h" #include "machine/53c7xx.h" +#include "machine/bacta_datalogger.h" #include "machine/mc146818.h" #include "machine/nvram.h" #include "machine/timer.h" diff --git a/src/mame/jpm/guab.cpp b/src/mame/jpm/guab.cpp index dd2dddc41d2..880f8975ec3 100644 --- a/src/mame/jpm/guab.cpp +++ b/src/mame/jpm/guab.cpp @@ -36,11 +36,10 @@ #include "emu.h" -#include "bacta_datalogger.h" - #include "cpu/m68000/m68000.h" #include "formats/guab_dsk.h" #include "imagedev/floppy.h" +#include "machine/bacta_datalogger.h" #include "machine/6840ptm.h" #include "machine/6850acia.h" #include "machine/clock.h" diff --git a/src/mame/jpm/jpmimpct.h b/src/mame/jpm/jpmimpct.h index 09baa76c86e..1d59b2f6c67 100644 --- a/src/mame/jpm/jpmimpct.h +++ b/src/mame/jpm/jpmimpct.h @@ -10,9 +10,8 @@ #pragma once -#include "bacta_datalogger.h" - #include "cpu/tms34010/tms34010.h" +#include "machine/bacta_datalogger.h" #include "machine/i8255.h" #include "machine/mc68681.h" #include "machine/meters.h" diff --git a/src/mame/jpm/jpmsys5.cpp b/src/mame/jpm/jpmsys5.cpp index ac52a288eb7..e99b7f1e020 100644 --- a/src/mame/jpm/jpmsys5.cpp +++ b/src/mame/jpm/jpmsys5.cpp @@ -35,8 +35,7 @@ #include "emu.h" #include "jpmsys5.h" -#include "bacta_datalogger.h" - +#include "machine/bacta_datalogger.h" #include "machine/clock.h" #include "machine/input_merger.h" #include "sound/saa1099.h" diff --git a/src/mame/konami/88games.h b/src/mame/konami/88games.h index 5856c71a1a0..39cf51b19de 100644 --- a/src/mame/konami/88games.h +++ b/src/mame/konami/88games.h @@ -12,7 +12,7 @@ #include "cpu/m6809/konami.h" #include "sound/upd7759.h" -#include "k051316.h" +#include "video/k051316.h" #include "k051960.h" #include "k052109.h" #include "konami_helper.h" diff --git a/src/mame/konami/ajax.cpp b/src/mame/konami/ajax.cpp index b0d878997c3..c6cdbe6be66 100644 --- a/src/mame/konami/ajax.cpp +++ b/src/mame/konami/ajax.cpp @@ -15,7 +15,6 @@ #include "emu.h" #include "konamipt.h" -#include "k051316.h" #include "k051960.h" #include "k052109.h" #include "konami_helper.h" @@ -27,6 +26,7 @@ #include "machine/watchdog.h" #include "sound/k007232.h" #include "sound/ymopm.h" +#include "video/k051316.h" #include "emupal.h" #include "speaker.h" diff --git a/src/mame/konami/bottom9.cpp b/src/mame/konami/bottom9.cpp index 3be8ea22262..f392c673633 100644 --- a/src/mame/konami/bottom9.cpp +++ b/src/mame/konami/bottom9.cpp @@ -17,7 +17,6 @@ #include "emu.h" #include "konamipt.h" -#include "k051316.h" #include "k051960.h" #include "k052109.h" #include "konami_helper.h" @@ -27,6 +26,7 @@ #include "machine/gen_latch.h" #include "machine/watchdog.h" #include "sound/k007232.h" +#include "video/k051316.h" #include "emupal.h" #include "screen.h" diff --git a/src/mame/konami/chqflag.h b/src/mame/konami/chqflag.h index 50204b54ed8..e6329ca3f30 100644 --- a/src/mame/konami/chqflag.h +++ b/src/mame/konami/chqflag.h @@ -13,7 +13,7 @@ #include "machine/bankdev.h" #include "sound/k007232.h" #include "k051960.h" -#include "k051316.h" +#include "video/k051316.h" #include "k051733.h" #include "konami_helper.h" #include "emupal.h" diff --git a/src/mame/konami/dbz.h b/src/mame/konami/dbz.h index 149e4123667..9fbf428cd09 100644 --- a/src/mame/konami/dbz.h +++ b/src/mame/konami/dbz.h @@ -14,7 +14,7 @@ #include "machine/timer.h" #include "k054156_k054157_k056832.h" #include "k053246_k053247_k055673.h" -#include "k053936.h" +#include "video/k053936.h" #include "k053251.h" #include "konami_helper.h" #include "tilemap.h" diff --git a/src/mame/konami/divebomb.h b/src/mame/konami/divebomb.h index 33403440b10..db356ef63e3 100644 --- a/src/mame/konami/divebomb.h +++ b/src/mame/konami/divebomb.h @@ -15,7 +15,7 @@ #include "machine/gen_latch.h" #include "machine/input_merger.h" #include "sound/sn76496.h" -#include "k051316.h" +#include "video/k051316.h" #include "emupal.h" #include "tilemap.h" diff --git a/src/mame/konami/konamigx.h b/src/mame/konami/konamigx.h index ebf548ea6c1..423be3313db 100644 --- a/src/mame/konami/konamigx.h +++ b/src/mame/konami/konamigx.h @@ -13,7 +13,7 @@ #include "sound/k054539.h" #include "k053246_k053247_k055673.h" #include "k053250.h" -#include "k053936.h" +#include "video/k053936.h" #include "k054156_k054157_k056832.h" #include "k054338.h" #include "k055555.h" diff --git a/src/mame/konami/overdriv.cpp b/src/mame/konami/overdriv.cpp index 3b668dfbef2..04ffb61c8e4 100644 --- a/src/mame/konami/overdriv.cpp +++ b/src/mame/konami/overdriv.cpp @@ -30,8 +30,8 @@ #include "machine/k053252.h" #include "machine/timer.h" -#include "k051316.h" #include "k053246_k053247_k055673.h" +#include "k053250.h" #include "k053251.h" #include "konami_helper.h" @@ -42,7 +42,7 @@ #include "machine/rescap.h" #include "sound/k053260.h" #include "sound/ymopm.h" -#include "k053250.h" +#include "video/k051316.h" #include "emupal.h" #include "screen.h" diff --git a/src/mame/konami/plygonet.cpp b/src/mame/konami/plygonet.cpp index 0bd537a85f1..492abf724f6 100644 --- a/src/mame/konami/plygonet.cpp +++ b/src/mame/konami/plygonet.cpp @@ -72,7 +72,7 @@ #include "machine/k056230.h" #include "machine/watchdog.h" #include "sound/k054539.h" -#include "k053936.h" +#include "video/k053936.h" #include "emupal.h" #include "screen.h" #include "speaker.h" diff --git a/src/mame/konami/rollerg.cpp b/src/mame/konami/rollerg.cpp index b43e66848d3..1ab1054f43c 100644 --- a/src/mame/konami/rollerg.cpp +++ b/src/mame/konami/rollerg.cpp @@ -14,7 +14,6 @@ #include "emu.h" -#include "k051316.h" #include "k053244_k053245.h" #include "konami_helper.h" @@ -24,6 +23,7 @@ #include "machine/watchdog.h" #include "sound/k053260.h" #include "sound/ymopl.h" +#include "video/k051316.h" #include "emupal.h" #include "speaker.h" diff --git a/src/mame/konami/rungun.h b/src/mame/konami/rungun.h index d8baf50c008..4da780ca987 100644 --- a/src/mame/konami/rungun.h +++ b/src/mame/konami/rungun.h @@ -13,7 +13,7 @@ #include "sound/k054539.h" #include "machine/k053252.h" #include "k053246_k053247_k055673.h" -#include "k053936.h" +#include "video/k053936.h" #include "machine/k054321.h" #include "konami_helper.h" #include "emupal.h" diff --git a/src/mame/konami/tmnt.h b/src/mame/konami/tmnt.h index 5a05d66b12f..f60120ea017 100644 --- a/src/mame/konami/tmnt.h +++ b/src/mame/konami/tmnt.h @@ -14,7 +14,7 @@ #include "k052109.h" #include "k051960.h" #include "k053251.h" -#include "k053936.h" +#include "video/k053936.h" #include "k054000.h" #include "konami_helper.h" #include "emupal.h" diff --git a/src/mame/konami/ultraman.h b/src/mame/konami/ultraman.h index d3cf46a213b..6e77c76a83b 100644 --- a/src/mame/konami/ultraman.h +++ b/src/mame/konami/ultraman.h @@ -13,7 +13,7 @@ #include "machine/gen_latch.h" #include "machine/input_merger.h" #include "k051960.h" -#include "k051316.h" +#include "video/k051316.h" #include "konami_helper.h" class ultraman_state : public driver_device diff --git a/src/mame/konami/wecleman.h b/src/mame/konami/wecleman.h index d775ae0b900..c2d3f250c1f 100644 --- a/src/mame/konami/wecleman.h +++ b/src/mame/konami/wecleman.h @@ -7,7 +7,7 @@ #include "machine/timer.h" #include "sound/k007232.h" -#include "k051316.h" +#include "video/k051316.h" #include "k007452.h" #include "emupal.h" #include "screen.h" diff --git a/src/mame/metro/metro.h b/src/mame/metro/metro.h index 069e43772a0..72adc88ad64 100644 --- a/src/mame/metro/metro.h +++ b/src/mame/metro/metro.h @@ -10,8 +10,6 @@ #pragma once -#include "k053936.h" - #include "machine/eepromser.h" #include "machine/gen_latch.h" #include "machine/timer.h" @@ -19,6 +17,7 @@ #include "sound/okim6295.h" #include "sound/ymopm.h" #include "video/imagetek_i4100.h" +#include "video/k053936.h" #include "screen.h" #include "tilemap.h" diff --git a/src/mame/misc/cave.cpp b/src/mame/misc/cave.cpp index f496d97672c..21ae337a543 100644 --- a/src/mame/misc/cave.cpp +++ b/src/mame/misc/cave.cpp @@ -87,10 +87,9 @@ Versions known to exist but not dumped: #include "emu.h" #include "cave.h" -#include "nmk112.h" - #include "cpu/m68000/m68000.h" #include "cpu/z80/z80.h" +#include "machine/nmk112.h" #include "machine/nvram.h" #include "machine/watchdog.h" #include "sound/ymopm.h" diff --git a/src/mame/misc/cave.h b/src/mame/misc/cave.h index 47c4fa128ab..1654cc1e306 100644 --- a/src/mame/misc/cave.h +++ b/src/mame/misc/cave.h @@ -11,16 +11,14 @@ ***************************************************************************/ -#include "tmap038.h" - #include "machine/eepromser.h" #include "machine/gen_latch.h" #include "machine/timer.h" #include "sound/okim6295.h" +#include "video/tmap038.h" #include "emupal.h" #include "screen.h" -#include "tilemap.h" class cave_state : public driver_device { diff --git a/src/mame/misc/freekick.cpp b/src/mame/misc/freekick.cpp index 03aea922dfd..c775a9e7508 100644 --- a/src/mame/misc/freekick.cpp +++ b/src/mame/misc/freekick.cpp @@ -109,8 +109,7 @@ TODO: #include "emu.h" #include "freekick.h" -#include "mc8123.h" - +#include "cpu/z80/mc8123.h" #include "cpu/z80/z80.h" #include "machine/i8255.h" #include "sound/sn76496.h" diff --git a/src/mame/misc/mcatadv.h b/src/mame/misc/mcatadv.h index 53963fb3a40..7cf0e2e729f 100644 --- a/src/mame/misc/mcatadv.h +++ b/src/mame/misc/mcatadv.h @@ -5,12 +5,10 @@ #pragma once -#include "tmap038.h" - #include "machine/watchdog.h" +#include "video/tmap038.h" #include "emupal.h" -#include "tilemap.h" class mcatadv_state : public driver_device { diff --git a/src/mame/nmk/nmk16.cpp b/src/mame/nmk/nmk16.cpp index b8ae97eb075..24894cb0d04 100644 --- a/src/mame/nmk/nmk16.cpp +++ b/src/mame/nmk/nmk16.cpp @@ -200,12 +200,11 @@ Reference of music tempo: #include "nmk004.h" -#include "nmk112.h" - #include "cpu/m68000/m68000.h" #include "cpu/pic16c5x/pic16c5x.h" #include "cpu/tlcs90/tlcs90.h" #include "cpu/z80/z80.h" +#include "machine/nmk112.h" #include "sound/okim6295.h" #include "sound/ymopm.h" #include "sound/ymopn.h" diff --git a/src/mame/nmk/powerins.cpp b/src/mame/nmk/powerins.cpp index e0f1e31e985..34ec1b7aa02 100644 --- a/src/mame/nmk/powerins.cpp +++ b/src/mame/nmk/powerins.cpp @@ -35,11 +35,10 @@ TODO: #include "powerins.h" -#include "nmk112.h" - #include "cpu/z80/z80.h" #include "cpu/m68000/m68000.h" #include "machine/gen_latch.h" +#include "machine/nmk112.h" #include "sound/okim6295.h" #include "sound/ymopn.h" #include "speaker.h" diff --git a/src/mame/nmk/quizpani.h b/src/mame/nmk/quizpani.h index 42dc5d9e084..9564183a131 100644 --- a/src/mame/nmk/quizpani.h +++ b/src/mame/nmk/quizpani.h @@ -5,7 +5,7 @@ #pragma once -#include "nmk112.h" +#include "machine/nmk112.h" #include "tilemap.h" diff --git a/src/mame/sanritsu/chinsan.cpp b/src/mame/sanritsu/chinsan.cpp index 8092b8aec8a..1b27dae2e5f 100644 --- a/src/mame/sanritsu/chinsan.cpp +++ b/src/mame/sanritsu/chinsan.cpp @@ -21,8 +21,7 @@ #include "emu.h" -#include "mc8123.h" - +#include "cpu/z80/mc8123.h" #include "cpu/z80/z80.h" #include "machine/i8255.h" #include "machine/nvram.h" diff --git a/src/mame/sega/naomigd.h b/src/mame/sega/naomigd.h index 1042359856f..d4863efe7b4 100644 --- a/src/mame/sega/naomigd.h +++ b/src/mame/sega/naomigd.h @@ -11,7 +11,7 @@ #include "machine/eepromser.h" #include "315-6154.h" #include "machine/idectrl.h" -#include "gdrom.h" +#include "bus/ata/gdrom.h" // For ide gdrom controller diff --git a/src/mame/sega/segae.cpp b/src/mame/sega/segae.cpp index 2c37bc0fd8c..2be20a5cc9f 100644 --- a/src/mame/sega/segae.cpp +++ b/src/mame/sega/segae.cpp @@ -296,10 +296,10 @@ GND 8A 8B GND #include "emu.h" #include "segaipt.h" +#include "cpu/z80/mc8123.h" #include "cpu/z80/z80.h" #include "machine/adc0804.h" #include "machine/i8255.h" -#include "mc8123.h" #include "machine/rescap.h" #include "segacrp2_device.h" #include "machine/upd4701.h" diff --git a/src/mame/sega/segas16b.cpp b/src/mame/sega/segas16b.cpp index c31aa34d588..9bf61c2b420 100644 --- a/src/mame/sega/segas16b.cpp +++ b/src/mame/sega/segas16b.cpp @@ -873,7 +873,7 @@ S11 S13 S15 S17 |EPR12194 - - - EPR12195 - - #include "segas16b.h" #include "segaipt.h" -#include "mc8123.h" +#include "cpu/z80/mc8123.h" #include "sound/okim6295.h" #include "speaker.h" diff --git a/src/mame/sega/system1.cpp b/src/mame/sega/system1.cpp index 1f7d3c59a69..78faadbfa1c 100644 --- a/src/mame/sega/system1.cpp +++ b/src/mame/sega/system1.cpp @@ -306,9 +306,9 @@ seem to have access to. #include "emu.h" #include "system1.h" -#include "mc8123.h" #include "segacrpt_device.h" +#include "cpu/z80/mc8123.h" #include "sound/sn76496.h" #include "speaker.h" diff --git a/src/mame/segacons/dccons.cpp b/src/mame/segacons/dccons.cpp index 255c1d42654..3535c08dd09 100644 --- a/src/mame/segacons/dccons.cpp +++ b/src/mame/segacons/dccons.cpp @@ -50,8 +50,8 @@ #include "dccons.h" #include "dc-ctrl.h" -#include "gdrom.h" +#include "bus/ata/gdrom.h" #include "cpu/arm7/arm7.h" #include "cpu/arm7/arm7core.h" #include "cpu/sh/sh4.h" diff --git a/src/mame/segacons/dccons.h b/src/mame/segacons/dccons.h index 23680acaa1c..1bad460cd38 100644 --- a/src/mame/segacons/dccons.h +++ b/src/mame/segacons/dccons.h @@ -6,7 +6,6 @@ #pragma once #include "dc.h" -#include "gdrom.h" #include "bus/ata/ataintf.h" #include "imagedev/chd_cd.h" diff --git a/src/mame/shared/bacta_datalogger.cpp b/src/mame/shared/bacta_datalogger.cpp deleted file mode 100644 index 43f9855bfd9..00000000000 --- a/src/mame/shared/bacta_datalogger.cpp +++ /dev/null @@ -1,218 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:James Wallace -#include "emu.h" -#include "bacta_datalogger.h" - -#define LOG_DATA (1U << 1) - -//#define VERBOSE (LOG_DATA) -//#define LOG_OUTPUT_STREAM std::cout - -#include "logmacro.h" - -#define LOGDATA(...) LOGMASKED(LOG_DATA, __VA_ARGS__) - -/*********************************************************************************************************** - BACTA Datalogger emulation - The British Amusement and Catering Trade Association created a standard for the tracking of statistics - and other features on British AWPs across hardware manufacturers. - The specification is very simple, a 1200 Baud null modem connection via RS232, with the logger sending an - ACK command (0x06) on receipt of a valid character, and NAK (0x15) on error. - In this emulation, the simplest possible device is simulated here, derived from the RS232 null_modem. - We only handle the feedback for acknowledgment, and limited logging. -************************************************************************************************************/ - -// device type definition -DEFINE_DEVICE_TYPE(BACTA_DATALOGGER, bacta_datalogger_device, "bacta_datalogger", "BACTA Datalogger") - -//------------------------------------------------- -// bacta_datalogger_device - constructor -//------------------------------------------------- - -bacta_datalogger_device::bacta_datalogger_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : - bacta_datalogger_device(mconfig, BACTA_DATALOGGER, tag, owner, clock) -{ -} - -bacta_datalogger_device::bacta_datalogger_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock) : - device_t(mconfig, BACTA_DATALOGGER, tag, owner, clock), - device_serial_interface(mconfig, *this), - m_rxd_handler(*this), - m_last_input(-1), - m_output_char(0) -{ -} - -void bacta_datalogger_device::device_start() -{ - m_rxd_handler.resolve_safe(); -} - -void bacta_datalogger_device::device_reset() -{ - int startbits = 1; - int databits = 8; - parity_t parity = device_serial_interface::PARITY_ODD; - stop_bits_t stopbits = device_serial_interface::STOP_BITS_1; - - set_data_frame(startbits, databits, parity, stopbits); - - set_tra_rate(1200); - - set_rcv_rate(1200); - - output_rxd(1); -} - -void bacta_datalogger_device::tx_queue() -{ - if (is_transmit_register_empty()) - { - if (m_output_char != 255) - { - set_tra_rate(1200); - transmit_register_setup(m_output_char); - m_output_char = 255; - } - } -} - -void bacta_datalogger_device::tra_callback() -{ - output_rxd(transmit_register_get_data_bit()); -} - -void bacta_datalogger_device::tra_complete() -{ - // Shut down transmitter until there's a character - set_tra_rate(attotime::never); - tx_queue(); -} - -void bacta_datalogger_device::rcv_complete() -{ - u8 data; - - receive_register_extract(); - - data = get_received_char(); - if (data != 0x00) - { - if (data > 0x80) - { - data &= ~0x80; - if ( data == m_last_input) - { - LOGDATA("Retransmission of %x\n",data); - } - m_last_input = data; - } - switch (data) - { - case 0x01: - LOGDATA("(%c) Prize 1 vend or 0x01\n",data); - break; - case 0x02: - LOGDATA("(%c) Prize 2 vend or 0x02\n",data); - break; - case 0x03: - LOGDATA("(%c) Prize 3 vend or 0x03\n",data); - break; - case 0x04: - LOGDATA("(%c) Prize 4 vend or 0x04\n",data); - break; - case 0x05: - LOGDATA("(%c) Remote Credit or 0x05\n",data); - break; - case 0x07: - LOGDATA("(%c) Idle or 0x07\n",data); - break; - case 0x08: - LOGDATA("(%c) Change or 0x08\n",data); - break; - case 0x09: - case 0x0a: - case 0x0b: - case 0x0c: - case 0x0d: - case 0x0e: - case 0x0f: - LOGDATA("(%c) User defined message or 0x0%x\n",data,data); - break; - case 0x2b: - LOGDATA("(%c) Cashbox door open 0x2b\n",data); - break; - case 0x2c: - LOGDATA("(%c) Cashbox door closed 0x2c\n",data); - break; - case 0x2d: - LOGDATA("(%c) Service door open 0x2d\n",data); - break; - case 0x2e: - LOGDATA("(%c) Service door closed 0x2e\n",data); - break; - case 0x60: - LOGDATA("(%c) Primary message (0x%x), next byte is message length\n",data,data); - break; - case 0x61: - LOGDATA("(%c) Coin Tube / Hopper Levels 0x61 \n",data); - break; - case 0x62: - LOGDATA("(%c) Secondary message (0x%x), next byte is message length\n",data,data); - break; - case 0x63: - LOGDATA("(%c) Critical Fault 0x63\n",data); - break; - case 0x64: - LOGDATA("(%c) Non Critical Fault 0x64\n",data); - break; - case 0x65: - LOGDATA("(%c) Manufacturer Message Header 0x65, next byte is message length\n",data); - break; - case 0x66: - LOGDATA("(%c) Potential Parameter Data request 0x66, not currently supported\n",data); - break; - case 0x67: - LOGDATA("(%c) Potential Parameter Report request 0x67, not currently supported\n",data); - break; - case 0x68: - LOGDATA("(%c) Multi-Stake Multi-Game message 0x68\n",data); - break; - case 0x69: - LOGDATA("(%c) Cashless source 0x69\n",data); - break; - case 0x70: - case 0x71: - case 0x72: - case 0x73: - case 0x74: - case 0x75: - case 0x76: - case 0x77: - case 0x78: - case 0x79: - case 0x7a: - case 0x7b: - case 0x7c: - case 0x7d: - case 0x7e: - case 0x7f: - LOGDATA("(%c) User defined message (0x%x), next byte is message length\n",data,data); - break; - - default: - LOGDATA("(%c) Received: %02x\n",data, data); - break; - } - m_output_char = 0x06;//ACK - tx_queue(); - } - else - { - if (data != 0x00) - { - m_output_char = 0x15;//NAK - tx_queue(); - } - } -} diff --git a/src/mame/shared/bacta_datalogger.h b/src/mame/shared/bacta_datalogger.h deleted file mode 100644 index c89dcbb68bd..00000000000 --- a/src/mame/shared/bacta_datalogger.h +++ /dev/null @@ -1,39 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:James Wallace -#ifndef MAME_BACTA_DATALOGGER_H -#define MAME_BACTA_DATALOGGER_H - -#include "diserial.h" - -class bacta_datalogger_device : public device_t, - public device_serial_interface -{ -public: - bacta_datalogger_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock = 0); - - virtual WRITE_LINE_MEMBER( write_txd ) {device_serial_interface::rx_w(state); } - auto rxd_handler() { return m_rxd_handler.bind(); } - - DECLARE_WRITE_LINE_MEMBER( output_rxd ) { m_rxd_handler(state); } - -protected: - bacta_datalogger_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock); - - virtual void device_start() override; - virtual void device_reset() override; - - virtual void tra_callback() override; - virtual void tra_complete() override; - virtual void rcv_complete() override; - -private: - void tx_queue(); - - devcb_write_line m_rxd_handler; - uint8_t m_last_input; - uint8_t m_output_char; -}; - -DECLARE_DEVICE_TYPE(BACTA_DATALOGGER, bacta_datalogger_device) - -#endif // MAME_BACTA_DATALOGGER_H diff --git a/src/mame/shared/gdrom.cpp b/src/mame/shared/gdrom.cpp deleted file mode 100644 index 59a7d154d56..00000000000 --- a/src/mame/shared/gdrom.cpp +++ /dev/null @@ -1,577 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:smf, Angelo Salese -/*************************************************************************** - - gdrom.c - Implementation of the Sega GD-ROM device - -***************************************************************************/ - -#include "emu.h" -#include "gdrom.h" - -#define LOG_WARN (1U << 1) -#define LOG_CMD (1U << 2) -#define LOG_XFER (1U << 3) - -#define VERBOSE (LOG_WARN | LOG_CMD) -//#define LOG_OUTPUT_STREAM std::cout -#include "logmacro.h" - -#define LOGWARN(...) LOGMASKED(LOG_WARN, __VA_ARGS__) -#define LOGCMD(...) LOGMASKED(LOG_CMD, __VA_ARGS__) -#define LOGXFER(...) LOGMASKED(LOG_XFER, __VA_ARGS__) - -#define GDROM_BUSY_STATE 0x00 -#define GDROM_PAUSE_STATE 0x01 -#define GDROM_STANDBY_STATE 0x02 -#define GDROM_PLAY_STATE 0x03 -#define GDROM_SEEK_STATE 0x04 -#define GDROM_SCAN_STATE 0x05 -#define GDROM_OPEN_STATE 0x06 -#define GDROM_NODISC_STATE 0x07 -#define GDROM_RETRY_STATE 0x08 -#define GDROM_ERROR_STATE 0x09 - - -/* - Officially not documented security-related packet commands: - - SYS_CHK_SECU (70h) Media security check - Parameters: 1byte - R0011111, R - "recheck" (it seems actual security check performed automatically at drive power on or when disc was inserted, so normally this and next command returns result of already performed check. - however, when MSB R bit is 1 will be forced media security recheck) - Result: none - SYS_REQ_SECU (71h) Request security data - Parameters: 1byte - always 0x1f - Result: a bit less than 1Kbyte chunk of data (length vary each time), contains real command reply obfuscated, which is extracted by such code: - - u8 reply[], real_reply[]; - for (u32 i = 0, offset = 0; i < length; i++) - { - offset++; - u32 skip = reply[offset] - 2; // normally skip value is < 0x10, might be used to identify real reply length - offset += skip; - real_reply[i] = reply[offset++]; - } - - Real reply is 43 byte: - struct sec_reply { - u8 check_result; // 0x1f - valid GD-ROM, 0x10 - valid Mil-CD (in this case following char[] fields is empty, 0x00-filled) - char key_id[10]; // presumable Disc ID (T-xxxxxx or HDR-xxxxx etc) - char key_maker_id[16]; // presumable "SEGA ENTERPRISES" - char hard_id[16]; // presumable "SEGA SEGAKATANA " - }; - - *_id fields names came from Dev.box "Checker BIOS" disassembly, contents meaning is guesswork because all the reply dumps we have now was dumped with Mil-CD disc inserted but not GD-ROM. - Presumable these data somehow encoded in GD-ROM disc HD area Lead-in (or Security Ring area ?), and compared with data in LD area IP.BIN by GD-drive firmware, - as described in Sega patent EP0935242A1 https://patents.google.com/patent/EP0935242A1 - - Dreamcast BIOS code verify only 1st result byte, if it's 5th bit (0x10) == 1. - Naomi DIMM firmware verify if result byte equal to 0x1f. - - SYS_CHG_COMD (72h) ??? Authentication for next command ? - Parameters: 1byte, probably key/password, in retail Dreamcast - 5th byte of unit SN# (located in flash ROM at 1A05Ah), 0 in Dev.box checker BIOS. - Result: none - - SYS_REQ_COMD (73h) Request command list - Parameters: none - Result: chunk of data where obfuscated real reply, see command 71. - real result: 14 bytes - codes of all regular (not security) packet commands supported by drive (00 10 11 12 13 14 15 16 20 21 22 30 31 40). - - Dreamcast BIOS SysCalls contain commands 0x72/73 routine, but it seems not used at practice. -*/ - -static const uint8_t GDROM_Cmd71_Reply[] = -{ - 0x96, 0x0B, 0x45, 0xF0, 0x7E, 0xFF, 0x3D, 0x06, 0x4D, 0x7D, 0x10, 0xBF, 0x07, 0x00, 0x73, 0xCF, - 0x9C, 0x00, 0xBC, 0x0C, 0x1C, 0xAF, 0x1C, 0x30, 0xE7, 0xA7, 0x03, 0xA8, 0x98, 0x00, 0xBD, 0x0F, - 0xBD, 0x5B, 0xAA, 0x50, 0x23, 0x39, 0x31, 0x10, 0x0E, 0x69, 0x13, 0xE5, 0x00, 0xD2, 0x0D, 0x66, - 0x54, 0xBF, 0x5F, 0xFD, 0x37, 0x74, 0xF4, 0x5B, 0x22, 0x00, 0xC6, 0x09, 0x0F, 0xCA, 0x93, 0xE8, - 0xA4, 0xAB, 0x00, 0x61, 0x0E, 0x2E, 0xE1, 0x4B, 0x76, 0x8B, 0x6A, 0xA5, 0x9C, 0xE6, 0x23, 0xC4, - 0x00, 0x4B, 0x06, 0x1B, 0x91, 0x01, 0x00, 0xE2, 0x0D, 0xCF, 0xCA, 0x38, 0x3A, 0xB9, 0xE7, 0x91, - 0xE5, 0xEF, 0x4B, 0x00, 0xD6, 0x09, 0xD3, 0x68, 0x3E, 0xC4, 0xAF, 0x2D, 0x00, 0x2A, 0x0D, 0xF9, - 0xFC, 0x78, 0xED, 0xAE, 0x99, 0xB3, 0x32, 0x5A, 0xE7, 0x00, 0x4C, 0x0A, 0x22, 0x97, 0x5B, 0x82, - 0x06, 0x7A, 0x4C, 0x00, 0x42, 0x0E, 0x57, 0x78, 0x46, 0xF5, 0x20, 0xFC, 0x6B, 0xCB, 0x01, 0x5B, - 0x86, 0x00, 0xE4, 0x0E, 0xB2, 0x26, 0xCD, 0x71, 0xE3, 0xA5, 0x33, 0x06, 0x8E, 0x9A, 0x50, 0x00, - 0x07, 0x07, 0xF5, 0x34, 0xEF, 0xE6, 0x00, 0x32, 0x0F, 0x13, 0x41, 0x59, 0x56, 0x0F, 0x02, 0x38, - 0x2A, 0x64, 0x2A, 0x07, 0x3E, 0x00, 0x52, 0x11, 0x2A, 0x1D, 0x5F, 0x76, 0x66, 0xA0, 0xB2, 0x2F, - 0x97, 0xC7, 0x5E, 0x6E, 0x52, 0xE2, 0x00, 0x58, 0x09, 0xCA, 0x89, 0xA5, 0xDF, 0x0A, 0xDE, 0x00, - 0x50, 0x06, 0x49, 0xB8, 0xB4, 0x00, 0x77, 0x05, 0x24, 0xE8, 0x00, 0xBB, 0x0C, 0x91, 0x89, 0xA2, - 0x8B, 0x62, 0xDE, 0x6A, 0xC6, 0x60, 0x00, 0xE7, 0x0F, 0x0F, 0x11, 0x96, 0x55, 0xD2, 0xBF, 0xE6, - 0x48, 0x0B, 0x5C, 0xAB, 0xDC, 0x00, 0xBA, 0x0A, 0x30, 0xD7, 0x48, 0x0E, 0x78, 0x63, 0x0C, 0x00, - 0xD2, 0x0D, 0xFB, 0x8A, 0xA3, 0xFE, 0xF8, 0x3A, 0xDD, 0x88, 0xA9, 0x4B, 0x00, 0xA2, 0x0A, 0x75, - 0x5D, 0x0D, 0x37, 0x24, 0xC5, 0x9D, 0x00, 0xF7, 0x0B, 0x25, 0xEF, 0xDB, 0x41, 0xE0, 0x52, 0x3E, - 0x4E, 0x00, 0xB7, 0x03, 0x00, 0xE5, 0x11, 0xB9, 0xDE, 0x5A, 0x57, 0xCF, 0xB9, 0x1A, 0xFC, 0x7F, - 0x26, 0xEE, 0x7B, 0xCD, 0x2B, 0x00, 0x4B, 0x08, 0xB8, 0x09, 0x70, 0x6A, 0x9F, 0x00, 0x4B, 0x11, - 0x8C, 0x15, 0x87, 0xA3, 0x05, 0x4F, 0x37, 0x8E, 0x63, 0xDE, 0xEF, 0x39, 0xFC, 0x4B, 0x00, 0xAB, - 0x10, 0x0B, 0x91, 0xAA, 0x0F, 0xE1, 0xE9, 0xAE, 0x69, 0x3A, 0xF8, 0x03, 0x69, 0xD2, 0x00, 0xE2, - 0x07, 0xC1, 0x5C, 0x3D, 0x82, 0x00, 0xA9, 0x08, 0x68, 0xC4, 0xAD, 0x2E, 0xD1, 0x00, 0xF7, 0x0E, - 0xC6, 0x47, 0xC8, 0xCD, 0x8E, 0x7C, 0x00, 0x5C, 0x95, 0xB9, 0xF4, 0x00, 0xE3, 0x04, 0x5B, 0x00, - 0x74, 0x07, 0x65, 0xC7, 0x84, 0x8E, 0x00, 0xC6, 0x07, 0x61, 0x80, 0x44, 0x3F, 0x00, 0xC8, 0x0E, - 0x72, 0x78, 0x47, 0xD3, 0xC2, 0x4D, 0xAF, 0xC0, 0x54, 0x13, 0x31, 0x00, 0xF7, 0x0D, 0x48, 0xD8, - 0xE2, 0x92, 0x9F, 0x7F, 0x2F, 0x44, 0x68, 0x33, 0x00, 0x0D, 0x10, 0xAB, 0xFE, 0xEA, 0x8E, 0x19, - 0x81, 0xF8, 0x6F, 0x7C, 0xDE, 0xE1, 0xB3, 0x06, 0x00, 0x4D, 0x11, 0x66, 0xAE, 0x4C, 0xF9, 0xB7, - 0x2F, 0xEE, 0xB0, 0x8E, 0x7E, 0xE1, 0x8D, 0x95, 0x6F, 0x00, 0xF4, 0x0D, 0x88, 0x9D, 0xCA, 0xE3, - 0xC4, 0xB2, 0x47, 0xBB, 0xA0, 0x69, 0x00, 0xF3, 0x0B, 0x48, 0x17, 0x41, 0x64, 0xA0, 0x0E, 0x71, - 0x82, 0x00, 0x34, 0x1E, 0x18, 0x4D, 0x85, 0x80, 0x4C, 0xA9, 0x0B, 0x66, 0x9B, 0x75, 0x13, 0x61, - 0x70, 0x27, 0x81, 0x7A, 0x02, 0xCD, 0x57, 0xAB, 0xDF, 0x02, 0x93, 0x52, 0x83, 0xDF, 0x48, 0xA8, - 0xA6, 0x9E, 0x74, 0x6F, 0x89, 0x03, 0x28, 0x25, 0x52, 0x96, 0xFF, 0x67, 0x7A, 0xD8, 0x3C, 0xB1, - 0x2C, 0x46, 0x84, 0xEF, 0xE1, 0xC1, 0xC6, 0xC9, 0xDC, 0x96, 0xAA, 0xA9, 0xC4, 0x82, 0x58, 0x27, - 0x57, 0x75, 0x67, 0x34, 0xFB, 0x3B, 0x25, 0xBF, 0xFB, 0x3B, 0xF6, 0x13, 0xEC, 0x96, 0xE5, 0x16, - 0x26, 0xFD, 0xA8, 0xDA, 0x1B, 0xC6, 0x50, 0x7F, 0x47, 0xFF, 0x08, 0x55, 0x08, 0xED, 0x00, 0x93, - 0x9B, 0xC4, 0x71, 0x67, 0xEC, 0xA6, 0xCC, 0x16, 0x20, 0x87, 0x47, 0x07, 0xA6, 0x00, 0x79, 0x5D, - 0x4F, 0xAB, 0xA1, 0x6F, 0x7A, 0x6B, 0x27, 0xC4, 0xDA, 0xA3, 0xC3, 0x94, 0x4F, 0x7F, 0xF3, 0xE5, - 0x1B, 0x6F, 0xCC, 0xE5, 0xF0, 0xE5, 0x9D, 0xC9, 0xAE, 0xFD, 0x39, 0xAC, 0x4C, 0xE5, 0x58, 0x83, - 0x25, 0x65, 0x92, 0x74, 0x9E, 0x81, 0xA0, 0xB6, 0xA9, 0x02, 0x9B, 0x07, 0xB6, 0xE7, 0x79, 0x57, - 0xD9, 0x4A, 0xCE, 0xFA, 0xB4, 0x94, 0x05, 0xCC, 0x86, 0x3C, 0xDD, 0x06, 0xCD, 0xA6, 0x24, 0x24, - 0xFA, 0xC1, 0xF9, 0x48, 0xC9, 0x0C, 0x6C, 0xC4, 0x96, 0x82, 0x17, 0xF6, 0x31, 0x09, 0xC4, 0xE2, - 0x77, 0xFD, 0xCF, 0x46, 0x18, 0xB2, 0x5F, 0x01, 0x6B, 0xD1, 0x7B, 0x56, 0xB8, 0x94, 0x4A, 0xE5, - 0x6C, 0x19, 0xF0, 0xC0, 0xB6, 0x70, 0x93, 0xF7, 0xD3, 0xD1, 0x2B, 0x6E, 0x7C, 0x53, 0x6D, 0x85, - 0xD1, 0x0C, 0x8B, 0x77, 0xEE, 0x90, 0xDA, 0x15, 0x55, 0xE0, 0x58, 0x09, 0x56, 0xFC, 0x31, 0x9F, - 0xAF, 0x46, 0xCB, 0xC3, 0x8D, 0x71, 0x75, 0xF2, 0x2C, 0xC3, 0xBB, 0xA1, 0xC4, 0xCF, 0x27, 0x56, - 0x7C, 0x9B, 0xFE, 0xAF, 0x3E, 0x4E, 0xB4, 0xCD, 0x6A, 0xAA, 0xF5, 0xF3, 0xE3, 0x22, 0x82, 0xE1, - 0xA5, 0x68, 0xB3, 0xDB, 0x8F, 0x9E, 0x5E, 0x7B, 0x90, 0xF0, 0x79, 0x3F, 0x52, 0x8C, 0x61, 0x88, - 0x76, 0xAE, 0x14, 0x63, 0x19, 0x0F, 0x1D, 0xCE, 0xA1, 0x63, 0x10, 0xB2, 0xE2, 0xD7, 0x94, 0xB1, - 0x33, 0xCB, 0x28, 0x85, 0x7D, 0x9B, 0xF5, 0xF4, 0x25, 0x50, 0x9B, 0xDB, 0x35, 0xA5, 0xB0, 0x9C, - 0x09, 0x92, 0xE3, 0x31, 0x40, 0xAB, 0x4D, 0xF4, 0x35, 0xE8, 0xB3, 0x0A, 0x21, 0xC3, 0x86, 0x9C, - 0xCB, 0x29, 0xA4, 0x77, 0x57, 0xBC, 0xD8, 0xDA, 0xA5, 0x82, 0x80, 0xE8, 0xCF, 0x72, 0x81, 0xAD, - 0x2E, 0x28, 0xFF, 0xD8, 0xB6, 0xD1, 0x2B, 0x97, 0x00, 0xFF, 0xE1, 0x06, 0x44, 0x39, 0x1C, 0x4B, - 0xAB, 0x19, 0x5B, 0x4D, 0xD6, 0x3E, 0x1B, 0x5C, 0x64, 0xBB, 0x32, 0x68, 0xF5, 0x7C, 0xC9, 0x9E, - 0xE8, 0xB4, 0x29, 0x1B, 0x7F, 0x4D, 0x80, 0x80, 0x7E, 0x8B, 0x1C, 0x0A, 0xE6, 0x9A, 0xBF, 0x49, - 0x1E, 0xC5, 0xB6, 0x67, 0x7D, 0x05, 0xE4, 0x90, 0x40, 0x4B, 0xAF, 0x9B, 0x52, 0xDE, 0x17, 0x80, - 0x81, 0x56, 0xEA, 0x3A, 0x53, 0x82, 0x8C, 0x62, 0xFB, 0x96, 0x97, 0x6F, 0xC1, 0x16, 0x78, 0xD4, - 0x7B, 0xE7, 0xB9, 0x5A, 0x2A, 0xEB, 0x87, 0x68, 0x33, 0xD3, 0x31, 0x45, 0xFA, 0xFE, 0xF4, 0x1C, - 0x90, 0x86, 0x73, 0x77, 0xD9, 0xA9, 0xD1, 0x4A, 0x4A, 0xCF, 0xAE, 0x23, 0xDB, 0xF9, 0x09, 0xD8, - 0x18, 0xDC, 0x6A, 0x0D, 0xE4, 0x19, 0x8C, 0x65, 0xC6, 0x64, 0xC7, 0xDC, 0xA9, 0xE3, 0x91, 0xB1, - 0x4C, 0xC8, 0xC1, 0x9E, 0x3B, 0x7F, 0xCB, 0xA3, 0xCF, 0xDD, 0xF0, 0x1D, 0x07, 0x6E, 0xDC, 0xCE, - 0x0D, 0xCD, 0x7E, 0x1E, 0x55, 0x11, 0x8B, 0xDF, 0x3A, 0xAB, 0xB6, 0x3B, 0x6E, 0x52, 0x7F, 0xA7, - 0x00, 0xD1, 0x33, 0xBE, 0xF2, 0x9B, 0xFC, 0x4A, 0xCF, 0x9D, 0x8F, 0xC6, 0xC4, 0x7B, 0xDA, 0xE7, - 0x2A, 0x1C, 0x26, 0x6E -}; - - -void gdrom_device::device_reset() -{ - static const uint8_t GDROM_Def_Cmd11_Reply[32] = - { - 0x00, 0x00, 0x00, 0x00, 0x00, 0xB4, 0x19, 0x00, 0x00, 0x08, 0x53, 0x45, 0x20, 0x20, 0x20, 0x20, - 0x20, 0x20, 0x52, 0x65, 0x76, 0x20, 0x36, 0x2E, 0x34, 0x32, 0x39, 0x39, 0x30, 0x33, 0x31, 0x36 - }; - - for(int i = 0;i<32;i++) - GDROM_Cmd11_Reply[i] = GDROM_Def_Cmd11_Reply[i]; - - atapi_cdrom_device::device_reset(); -} - -// scsicd_exec_command -// -// Execute a SCSI command. - -void gdrom_device::ExecCommand() -{ - switch ( command[0] ) - { - case 0x11: // REQ_MODE - m_phase = SCSI_PHASE_DATAIN; - m_status_code = SCSI_STATUS_CODE_GOOD; - LOGCMD("REQ_MODE %02x %02x %02x %02x %02x %02x\n", - command[0], command[1], - command[2], command[3], - command[4], command[5] - ); -// if (SCSILengthFromUINT8( &command[ 4 ] ) < 32) return -1; - transferOffset = command[2]; - m_transfer_length = SCSILengthFromUINT8( &command[ 4 ] ); - break; - - case 0x12: // SET_MODE - m_phase = SCSI_PHASE_DATAOUT; - m_status_code = SCSI_STATUS_CODE_GOOD; - //transferOffset = command[2]; - m_transfer_length = SCSILengthFromUINT8( &command[ 4 ] ); - LOGCMD("SET_MODE %02x %02x\n", command[2], command[4]); - break; - - case 0x30: // CD_READ - if (command[1] & 1) - { - m_transfer_length = 0; - throw emu_fatalerror("GDROM: MSF mode used for CD_READ, unsupported"); - } - else - { - m_lba = (command[2]<<16 | command[3]<<8 | command[4]) - 150; - m_blocks = command[8]<<16 | command[9]<<8 | command[10]; - - read_type = (command[1] >> 1) & 7; - data_select = (command[1]>>4) & 0xf; - - if (read_type != 2) // mode 1 - { - throw emu_fatalerror("GDROM: Unhandled read_type %d", read_type); - } - - if (data_select != 2) // just sector data - { - throw emu_fatalerror("GDROM: Unhandled data_select %d", data_select); - } - - LOGCMD("CD_READ %02x %02x\n", command[2], command[4]); - LOGCMD(" LBA %x for %d blocks (%d bytes, read type %d, data select %d)\n", - m_lba, m_blocks, - m_blocks * m_sector_bytes, read_type, data_select - ); - - if (m_num_subblocks > 1) - { - m_cur_subblock = m_lba % m_num_subblocks; - m_lba /= m_num_subblocks; - } - else - { - m_cur_subblock = 0; - } - - if (m_cdda != nullptr) - { - m_cdda->stop_audio(); - } - - m_phase = SCSI_PHASE_DATAIN; - m_status_code = SCSI_STATUS_CODE_GOOD; - m_transfer_length = m_blocks * m_sector_bytes; - } - break; - - // READ TOC (GD-ROM ver.) - case 0x14: - { - if (m_cdrom == nullptr) - { - m_phase = SCSI_PHASE_STATUS; - m_status_code = SCSI_STATUS_CODE_CHECK_CONDITION; - m_transfer_length = 0; - break; - } - - // TODO: is this correct? - int start_trk = command[2]; - int end_trk = m_cdrom->get_last_track(); - int length; - int allocation_length = SCSILengthFromUINT16( &command[ 3 ] ); - - if( start_trk == 0 ) - { - start_trk = 1; - } - if( start_trk == 0xaa ) - { - end_trk = start_trk; - } - - length = 4 + ( 8 * ( ( end_trk - start_trk ) + 1 ) ); - if( length > allocation_length ) - { - length = allocation_length; - } - else if( length < 4 ) - { - length = 4; - } - - if (m_cdda != nullptr) - { - m_cdda->stop_audio(); - } - - m_phase = SCSI_PHASE_DATAIN; - m_status_code = SCSI_STATUS_CODE_GOOD; - m_transfer_length = length; - break; - } - - case 0x70: // security check, return no data, always followed by cmd 0x71, command[1] parameter can be 0x1f or 0x9f - m_phase = SCSI_PHASE_STATUS; - m_status_code = SCSI_STATUS_CODE_GOOD; - m_transfer_length = 0; - break; - - case 0x71: - m_phase = SCSI_PHASE_DATAIN; - m_status_code = SCSI_STATUS_CODE_GOOD; - m_transfer_length = sizeof(GDROM_Cmd71_Reply); - break; - - case 0x40: - if(command[1] & 0xf) - { - m_phase = SCSI_PHASE_DATAIN; - m_status_code = SCSI_STATUS_CODE_GOOD; - m_transfer_length = 0xe; - } - else - { - LOGWARN("command 0x40: unhandled subchannel request\n"); - } - break; - - default: - t10mmc::ExecCommand(); - break; - } -} - -// scsicd_read_data -// -// Read data from the device resulting from the execution of a command - -void gdrom_device::ReadData( uint8_t *data, int dataLength ) -{ - int i; - uint8_t tmp_buffer[2048]; - - switch ( command[0] ) - { - case 0x11: // REQ_MODE - LOGCMD("REQ_MODE dataLength %d\n", dataLength); - memcpy(data, &GDROM_Cmd11_Reply[transferOffset], (dataLength >= 32-transferOffset) ? 32-transferOffset : dataLength); - break; - - case 0x30: // CD_READ - LOGCMD("CD_READ read %x dataLength,\n", dataLength); - if ((m_cdrom) && (m_blocks)) - { - while (dataLength > 0) - { - if (!m_cdrom->read_data(m_lba, tmp_buffer, cdrom_file::CD_TRACK_MODE1)) - { - LOGWARN("CD read error!\n"); - } - - LOGXFER("True LBA: %d, buffer half: %d\n", m_lba, m_cur_subblock * m_sector_bytes); - - memcpy(data, &tmp_buffer[m_cur_subblock * m_sector_bytes], m_sector_bytes); - - m_cur_subblock++; - if (m_cur_subblock >= m_num_subblocks) - { - m_cur_subblock = 0; - - m_lba++; - m_blocks--; - } - - m_last_lba = m_lba; - dataLength -= m_sector_bytes; - data += m_sector_bytes; - } - } - break; - - case 0x14: // READ TOC (GD-ROM ver.) - /* - Track numbers are problematic here: 0 = lead-in, 0xaa = lead-out. - That makes sense in terms of how real-world CDs are referred to, but - our internal routines for tracks use "0" as track 1. That probably - should be fixed... - */ - LOGCMD("READ TOC format = %d time=%d\n", - command[2] & 0xf, (command[1] >> 1) & 1 - ); - switch (command[2] & 0x0f) - { - case 0: // normal - { - int start_trk; - int end_trk; - int len; - int in_len; - int dptr; - uint32_t tstart; - - start_trk = command[2]; - if( start_trk == 0 ) - { - start_trk = 1; - } - - end_trk = m_cdrom->get_last_track(); - len = (end_trk * 8) + 2; - - // the returned TOC DATA LENGTH must be the full amount, - // regardless of how much we're able to pass back due to in_len - dptr = 0; - data[dptr++] = (len>>8) & 0xff; - data[dptr++] = (len & 0xff); - data[dptr++] = 1; - data[dptr++] = end_trk; - - if( start_trk == 0xaa ) - { - end_trk = 0xaa; - } - - in_len = command[3]<<8 | command[4]; - - for (i = start_trk; i <= end_trk; i++) - { - int cdrom_track = i; - if( cdrom_track != 0xaa ) - { - cdrom_track--; - } - - if( dptr >= in_len ) - { - break; - } - - data[dptr++] = 0; - data[dptr++] = m_cdrom->get_adr_control(cdrom_track); - data[dptr++] = i; - data[dptr++] = 0; - - tstart = m_cdrom->get_track_start(cdrom_track); - if ((command[1]&2)>>1) - tstart = cdrom_file::lba_to_msf(tstart); - data[dptr++] = (tstart>>24) & 0xff; - data[dptr++] = (tstart>>16) & 0xff; - data[dptr++] = (tstart>>8) & 0xff; - data[dptr++] = (tstart & 0xff); - } - - break; - } - default: - LOGWARN("Unhandled READ TOC format %d\n", command[2]&0xf); - break; - } - break; - - case 0x71: - LOGCMD("SYS_REQ_SECU\n"); - memcpy(data, &GDROM_Cmd71_Reply[0], sizeof(GDROM_Cmd71_Reply)); - if (is_real_gdrom_disc) - data[10] = 0x1f; // needed by dimm board firmware - break; - - case 0x40: // Get Subchannel status - data[0] = 0; // Reserved - data[1] = 0x15; // Audio Playback status (todo) - data[2] = 0; - data[3] = 0x0e; // header size - data[4] = 0; // ? - data[5] = 1; // Track Number - data[6] = 1; // gap #1 - data[7] = 0; // ? - data[8] = 0; // ? - data[9] = 0; // ? - data[0xa] = 0; // ? - data[0xb] = 0; // FAD >> 16 - data[0xc] = 0; // FAD >> 8 - data[0xd] = 0x96; // FAD >> 0 - break; - - default: - t10mmc::ReadData( data, dataLength ); - break; - } -} - -// scsicd_write_data -// -// Write data to the CD-ROM device as part of the execution of a command - -void gdrom_device::WriteData( uint8_t *data, int dataLength ) -{ - switch (command[ 0 ]) - { - case 0x12: // SET_MODE - memcpy(&GDROM_Cmd11_Reply[transferOffset], data, (dataLength >= 32-transferOffset) ? 32-transferOffset : dataLength); - break; - - default: - t10mmc::WriteData( data, dataLength ); - break; - } -} - -void gdrom_device::SetDevice(void *device) -{ - t10mmc::SetDevice(device); - - // try to find if the mounted chd is from an actual gd-rom disc - if (m_cdrom) - if (m_cdrom->get_toc().flags & cdrom_file::CD_FLAG_GDROM) - is_real_gdrom_disc = true; -} - -// device type definition -DEFINE_DEVICE_TYPE(GDROM, gdrom_device, "gdrom", "GD-ROM") - -gdrom_device::gdrom_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : - atapi_cdrom_device(mconfig, GDROM, tag, owner, clock), - is_real_gdrom_disc(false) -{ -} - -void gdrom_device::device_start() -{ - save_item(NAME(read_type)); - save_item(NAME(data_select)); - save_item(NAME(transferOffset)); - - /// TODO: split identify buffer into another method as device_start() should be called after it's filled in, but the atapi_cdrom_device has it's own. - atapi_cdrom_device::device_start(); - - memset(m_identify_buffer, 0, sizeof(m_identify_buffer)); - - m_identify_buffer[0] = 0x8600; // ATAPI device, cmd set 6 compliant, DRQ within 3 ms of PACKET command - - m_identify_buffer[23] = ('S' << 8) | 'E'; - m_identify_buffer[24] = (' ' << 8) | ' '; - m_identify_buffer[25] = (' ' << 8) | ' '; - m_identify_buffer[26] = (' ' << 8) | ' '; - - m_identify_buffer[27] = ('C' << 8) | 'D'; - m_identify_buffer[28] = ('-' << 8) | 'R'; - m_identify_buffer[29] = ('O' << 8) | 'M'; - m_identify_buffer[30] = (' ' << 8) | 'D'; - m_identify_buffer[31] = ('R' << 8) | 'I'; - m_identify_buffer[32] = ('V' << 8) | 'E'; - m_identify_buffer[33] = (' ' << 8) | ' '; - m_identify_buffer[34] = (' ' << 8) | ' '; - m_identify_buffer[35] = ('6' << 8) | '.'; - m_identify_buffer[36] = ('4' << 8) | '2'; - m_identify_buffer[37] = (' ' << 8) | ' '; - m_identify_buffer[38] = (' ' << 8) | ' '; - m_identify_buffer[39] = (' ' << 8) | ' '; - m_identify_buffer[40] = (' ' << 8) | ' '; - m_identify_buffer[41] = (' ' << 8) | ' '; - m_identify_buffer[42] = (' ' << 8) | ' '; - m_identify_buffer[43] = (' ' << 8) | ' '; - m_identify_buffer[44] = (' ' << 8) | ' '; - m_identify_buffer[45] = (' ' << 8) | ' '; - m_identify_buffer[46] = (' ' << 8) | ' '; - - m_identify_buffer[49] = 0x0400; // IORDY may be disabled - - m_identify_buffer[63]=7; // multi word dma mode 0-2 supported - m_identify_buffer[64]=1; // PIO mode 3 supported -} - -void gdrom_device::process_buffer() -{ - atapi_hle_device::process_buffer(); - // HACK: find out when this should be updated - m_sector_number = 0x80 | GDROM_PAUSE_STATE; -} - -void gdrom_device::signature() -{ - atapi_hle_device::signature(); - - // naomi dimm board firmware needs the upper nibble to be 8 at the beginning - if (is_real_gdrom_disc) - m_sector_number = 0x81; -} diff --git a/src/mame/shared/gdrom.h b/src/mame/shared/gdrom.h deleted file mode 100644 index 2d67e274c0d..00000000000 --- a/src/mame/shared/gdrom.h +++ /dev/null @@ -1,46 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:smf, Angelo Salese -/*************************************************************************** - - gdrom.h - -***************************************************************************/ - -#ifndef MAME_MACHINE_GDROM_H -#define MAME_MACHINE_GDROM_H - -#pragma once - -#include "bus/ata/atapicdr.h" - -class gdrom_device : public atapi_cdrom_device -{ -public: - gdrom_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - - // Sega GD-ROM handler - - virtual void ExecCommand() override; - virtual void WriteData( uint8_t *data, int dataLength ) override; - virtual void ReadData( uint8_t *data, int dataLength ) override; - -protected: - virtual void process_buffer() override; - virtual void signature() override; - virtual void SetDevice(void *device) override; - - // device-level overrides - virtual void device_start() override; - virtual void device_reset() override; - -private: - uint8_t GDROM_Cmd11_Reply[32]; - uint32_t read_type = 0; // for command 0x30 only - uint32_t data_select = 0; // for command 0x30 only - uint32_t transferOffset = 0; - bool is_real_gdrom_disc; -}; - -DECLARE_DEVICE_TYPE(GDROM, gdrom_device) - -#endif // MAME_MACHINE_GDROM_H diff --git a/src/mame/shared/k051316.cpp b/src/mame/shared/k051316.cpp deleted file mode 100644 index 5f59e3f8b83..00000000000 --- a/src/mame/shared/k051316.cpp +++ /dev/null @@ -1,304 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Fabio Priuli,Acho A. Tang, R. Belmont -/* -Konami 051316 PSAC ------- -Manages a 32x32 tilemap (16x16 tiles, 512x512 pixels) which can be zoomed, -distorted and rotated. -It uses two internal 24 bit counters which are incremented while scanning the -picture. The coordinates of the pixel in the tilemap that has to be drawn to -the current beam position are the counters / (2^11). -The chip doesn't directly generate the color information for the pixel, it -just generates a 24 bit address (whose top 16 bits are the contents of the -tilemap RAM), and a "visible" signal. It's up to external circuitry to convert -the address into a pixel color. Most games seem to use 4bpp graphics, but Ajax -uses 7bpp. -If the value in the internal counters is out of the visible range (0..511), it -is truncated and the corresponding address is still generated, but the "visible" -signal is not asserted. The external circuitry might ignore that signal and -still generate the pixel, therefore making the tilemap a continuous playfield -that wraps around instead of a large sprite. - -control registers -000-001 X counter starting value / 256 -002-003 amount to add to the X counter after each horizontal pixel -004-005 amount to add to the X counter after each line (0 = no rotation) -006-007 Y counter starting value / 256 -008-009 amount to add to the Y counter after each horizontal pixel (0 = no rotation) -00a-00b amount to add to the Y counter after each line -00c-00d ROM bank to read, used during ROM testing -00e bit 0 = enable ROM reading (active low). This only makes the chip output the - requested address: the ROM is actually read externally, not through - the chip's data bus. - bit 1 = unknown - bit 2 = unknown -00f unused - -*/ - -#include "emu.h" -#include "k051316.h" - - -#define VERBOSE 0 -#include "logmacro.h" - - -DEFINE_DEVICE_TYPE(K051316, k051316_device, "k051316", "K051316 PSAC") - - -const gfx_layout k051316_device::charlayout4 = -{ - 16,16, - RGN_FRAC(1,1), - 4, - { 0, 1, 2, 3 }, - { 0*4, 1*4, 2*4, 3*4, 4*4, 5*4, 6*4, 7*4, - 8*4, 9*4, 10*4, 11*4, 12*4, 13*4, 14*4, 15*4 }, - { 0*64, 1*64, 2*64, 3*64, 4*64, 5*64, 6*64, 7*64, - 8*64, 9*64, 10*64, 11*64, 12*64, 13*64, 14*64, 15*64 }, - 128*8 -}; - -const gfx_layout k051316_device::charlayout7 = -{ - 16,16, - RGN_FRAC(1,1), - 7, - { 1,2,3,4,5,6,7 }, - { 0*8, 1*8, 2*8, 3*8, 4*8, 5*8, 6*8, 7*8, - 8*8, 9*8, 10*8, 11*8, 12*8, 13*8, 14*8, 15*8 }, - { 0*128, 1*128, 2*128, 3*128, 4*128, 5*128, 6*128, 7*128, - 8*128, 9*128, 10*128, 11*128, 12*128, 13*128, 14*128, 15*128 }, - 256*8 -}; - -const gfx_layout k051316_device::charlayout8 = -{ - 16,16, - RGN_FRAC(1,1), - 8, - { 0,1,2,3,4,5,6,7 }, - { 0*8, 1*8, 2*8, 3*8, 4*8, 5*8, 6*8, 7*8, - 8*8, 9*8, 10*8, 11*8, 12*8, 13*8, 14*8, 15*8 }, - { 0*128, 1*128, 2*128, 3*128, 4*128, 5*128, 6*128, 7*128, - 8*128, 9*128, 10*128, 11*128, 12*128, 13*128, 14*128, 15*128 }, - 256*8 -}; - - -GFXDECODE_MEMBER( k051316_device::gfxinfo ) - GFXDECODE_DEVICE(DEVICE_SELF, 0, charlayout4, 0, 1) -GFXDECODE_END - -GFXDECODE_MEMBER( k051316_device::gfxinfo7 ) - GFXDECODE_DEVICE(DEVICE_SELF, 0, charlayout7, 0, 1) -GFXDECODE_END - -GFXDECODE_MEMBER( k051316_device::gfxinfo8 ) - GFXDECODE_DEVICE(DEVICE_SELF, 0, charlayout8, 0, 1) -GFXDECODE_END - -GFXDECODE_MEMBER( k051316_device::gfxinfo4_ram ) - GFXDECODE_DEVICE_RAM(DEVICE_SELF, 0, charlayout4, 0, 1) -GFXDECODE_END - - -k051316_device::k051316_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : device_t(mconfig, K051316, tag, owner, clock) - , device_gfx_interface(mconfig, *this, gfxinfo) - , m_zoom_rom(*this, DEVICE_SELF) - , m_dx(0) - , m_dy(0) - , m_wrap(0) - , m_pixels_per_byte(2) // 4bpp layout is default - , m_layermask(0) - , m_k051316_cb(*this) -{ -} - -void k051316_device::set_bpp(int bpp) -{ - switch(bpp) - { - case 4: - set_info(gfxinfo); - m_pixels_per_byte = 2; - break; - case 7: - set_info(gfxinfo7); - m_pixels_per_byte = 1; - break; - case 8: - set_info(gfxinfo8); - m_pixels_per_byte = 1; - break; - case -4: - set_info(gfxinfo4_ram); - m_pixels_per_byte = 2; - break; - default: - fatalerror("Unsupported bpp\n"); - } -} - - - -//------------------------------------------------- -// device_start - device-specific startup -//------------------------------------------------- - -void k051316_device::device_start() -{ - // assumes it can make an address mask with .length() - 1 - assert(!(m_zoom_rom.length() & (m_zoom_rom.length() - 1))); - - if (!palette().device().started()) - throw device_missing_dependencies(); - - // bind callbacks - m_k051316_cb.resolve(); - - decode_gfx(); - gfx(0)->set_colors(palette().entries() / gfx(0)->depth()); - - m_tmap = &machine().tilemap().create(*this, tilemap_get_info_delegate(*this, FUNC(k051316_device::get_tile_info)), TILEMAP_SCAN_ROWS, 16, 16, 32, 32); - m_ram.resize(0x800); - memset(&m_ram[0], 0, 0x800); - - if (m_layermask) - { - m_tmap->map_pens_to_layer(0, 0, 0, TILEMAP_PIXEL_LAYER1); - m_tmap->map_pens_to_layer(0, m_layermask, m_layermask, TILEMAP_PIXEL_LAYER0); - } - else - m_tmap->set_transparent_pen(0); - - save_item(NAME(m_ram)); - save_item(NAME(m_ctrlram)); - save_item(NAME(m_wrap)); - -} - -//------------------------------------------------- -// device_reset - device-specific reset -//------------------------------------------------- - -void k051316_device::device_reset() -{ - memset(m_ctrlram, 0, 0x10); -} - -/***************************************************************************** - DEVICE HANDLERS -*****************************************************************************/ - -u8 k051316_device::read(offs_t offset) -{ - return m_ram[offset]; -} - -void k051316_device::write(offs_t offset, u8 data) -{ - m_ram[offset] = data; - m_tmap->mark_tile_dirty(offset & 0x3ff); -} - - -u8 k051316_device::rom_r(offs_t offset) -{ - assert (m_zoom_rom.found()); - - if ((m_ctrlram[0x0e] & 0x01) == 0) - { - int addr = offset + (m_ctrlram[0x0c] << 11) + (m_ctrlram[0x0d] << 19); - addr /= m_pixels_per_byte; - addr &= m_zoom_rom.length() - 1; - - // popmessage("%s: offset %04x addr %04x", machine().describe_context(), offset, addr); - - return m_zoom_rom[addr]; - } - else - { - //logerror("%s: read 051316 ROM offset %04x but reg 0x0c bit 0 not clear\n", machine().describe_context(), offset); - return 0; - } -} - -void k051316_device::ctrl_w(offs_t offset, u8 data) -{ - m_ctrlram[offset] = data; - //if (offset >= 0x0c) logerror("%s: write %02x to 051316 reg %x\n", machine().describe_context(), data, offset); -} - -// some games (ajax, rollerg, ultraman, etc.) have external logic that can enable or disable wraparound dynamically -void k051316_device::wraparound_enable( int status ) -{ - m_wrap = status; -} - -/*************************************************************************** - - Callbacks for the TileMap code - -***************************************************************************/ - -TILE_GET_INFO_MEMBER(k051316_device::get_tile_info) -{ - int code = m_ram[tile_index]; - int color = m_ram[tile_index + 0x400]; - int flags = 0; - - m_k051316_cb(&code, &color, &flags); - - tileinfo.set(0, - code, - color, - flags); -} - - -void k051316_device::zoom_draw( screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, int flags, uint32_t priority ) -{ - uint32_t startx, starty; - int incxx, incxy, incyx, incyy; - - startx = 256 * ((int16_t)(256 * m_ctrlram[0x00] + m_ctrlram[0x01])); - incxx = (int16_t)(256 * m_ctrlram[0x02] + m_ctrlram[0x03]); - incyx = (int16_t)(256 * m_ctrlram[0x04] + m_ctrlram[0x05]); - starty = 256 * ((int16_t)(256 * m_ctrlram[0x06] + m_ctrlram[0x07])); - incxy = (int16_t)(256 * m_ctrlram[0x08] + m_ctrlram[0x09]); - incyy = (int16_t)(256 * m_ctrlram[0x0a] + m_ctrlram[0x0b]); - - startx -= (16 + m_dy) * incyx; - starty -= (16 + m_dy) * incyy; - - startx -= (89 + m_dx) * incxx; - starty -= (89 + m_dx) * incxy; - - m_tmap->draw_roz(screen, bitmap, cliprect, startx << 5, starty << 5, - incxx << 5, incxy << 5, incyx << 5, incyy << 5, - m_wrap, - flags, priority); - -#if 0 - popmessage("%02x%02x%02x%02x %02x%02x%02x%02x %02x%02x%02x%02x %02x%02x%02x%02x", - m_ctrlram[0x00], - m_ctrlram[0x01], - m_ctrlram[0x02], - m_ctrlram[0x03], - m_ctrlram[0x04], - m_ctrlram[0x05], - m_ctrlram[0x06], - m_ctrlram[0x07], - m_ctrlram[0x08], - m_ctrlram[0x09], - m_ctrlram[0x0a], - m_ctrlram[0x0b], - m_ctrlram[0x0c], /* bank for ROM testing */ - m_ctrlram[0x0d], - m_ctrlram[0x0e], /* 0 = test ROMs */ - m_ctrlram[0x0f]); -#endif -} diff --git a/src/mame/shared/k051316.h b/src/mame/shared/k051316.h deleted file mode 100644 index db3df893986..00000000000 --- a/src/mame/shared/k051316.h +++ /dev/null @@ -1,86 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Fabio Priuli,Acho A. Tang, R. Belmont -#ifndef MAME_VIDEO_K051316_H -#define MAME_VIDEO_K051316_H - -#pragma once - -#include "tilemap.h" - - -#define K051316_CB_MEMBER(_name) void _name(int *code, int *color, int *flags) - - -class k051316_device : public device_t, public device_gfx_interface -{ -public: - using zoom_delegate = device_delegate; - - k051316_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - - static const gfx_layout charlayout4; - static const gfx_layout charlayout7; - static const gfx_layout charlayout8; - DECLARE_GFXDECODE_MEMBER(gfxinfo); - DECLARE_GFXDECODE_MEMBER(gfxinfo7); - DECLARE_GFXDECODE_MEMBER(gfxinfo8); - DECLARE_GFXDECODE_MEMBER(gfxinfo4_ram); - - // configuration - template void set_zoom_callback(T &&... args) { m_k051316_cb.set(std::forward(args)...); } - void set_wrap(int wrap) { m_wrap = wrap; } - void set_bpp(int bpp); - void set_layermask(int mask) { m_layermask = mask; } - void set_offsets(int x_offset, int y_offset) - { - m_dx = x_offset; - m_dy = y_offset; - } - - /* - The callback is passed: - - code (range 00-FF, contents of the first tilemap RAM byte) - - color (range 00-FF, contents of the first tilemap RAM byte). Note that bit 6 - seems to be hardcoded as flip X. - The callback must put: - - in code the resulting tile number - - in color the resulting color index - - if necessary, put flags for the TileMap code in the tile_info - structure (e.g. TILE_FLIPX) - */ - - u8 read(offs_t offset); - void write(offs_t offset, u8 data); - u8 rom_r(offs_t offset); - void ctrl_w(offs_t offset, u8 data); - void zoom_draw(screen_device &screen, bitmap_ind16 &bitmap,const rectangle &cliprect,int flags,uint32_t priority); - void wraparound_enable(int status); - - void mark_gfx_dirty(offs_t byteoffset) { gfx(0)->mark_dirty(byteoffset * m_pixels_per_byte / (16 * 16)); } - void mark_tmap_dirty() { m_tmap->mark_all_dirty(); } - -protected: - // device-level overrides - virtual void device_start() override; - virtual void device_reset() override; - -private: - // internal state - std::vector m_ram; - uint8_t m_ctrlram[16]; - tilemap_t *m_tmap = nullptr; - - optional_region_ptr m_zoom_rom; - - int m_dx, m_dy; - int m_wrap; - int m_pixels_per_byte; - int m_layermask; - zoom_delegate m_k051316_cb; - - TILE_GET_INFO_MEMBER(get_tile_info); -}; - -DECLARE_DEVICE_TYPE(K051316, k051316_device) - -#endif // MAME_VIDEO_K051316_H diff --git a/src/mame/shared/k053936.cpp b/src/mame/shared/k053936.cpp deleted file mode 100644 index c9900430b53..00000000000 --- a/src/mame/shared/k053936.cpp +++ /dev/null @@ -1,855 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:David Haywood -/* */ - -#include "emu.h" -#include "k053936.h" - -#define VERBOSE 0 -#include "logmacro.h" - - -// Localized K053936/ROZ+ -#define K053936_MAX_CHIPS 2 - -static rectangle K053936_cliprect[K053936_MAX_CHIPS]; -static int K053936_offset[K053936_MAX_CHIPS][2] = {{0,0},{0,0}}; -static int K053936_clip_enabled[K053936_MAX_CHIPS] = {0,0}; -static int K053936_wraparound[K053936_MAX_CHIPS]; - - - - -/***************************************************************************/ -/* */ -/* 053936 */ -/* */ -/***************************************************************************/ - -/* - -053936 ------- -Evolution of the 051316. The data bus is 16-bit instead of 8-bit. -When used in "simple" mode it can generate the same effects of the 051316, but it -doesn't have internal tilemap RAM, so it just generates a couple of X/Y coordinates -indicating the pixel to display at each moment. Therefore, the tilemap and tile -sizes are not fixed. -The important addition over the 051316 is 512x4 words of internal RAM used to control -rotation and zoom scanline by scanline instead that on the whole screen, allowing for -effects like linescroll (Super Slams) or 3D rotation of the tilemap (Golfing Greats, -Premier Soccer). - -control registers -000 X counter starting value / 256 -001 Y counter starting value / 256 -002 ["simple" mode only] amount to add to the X counter after each line (0 = no rotation) -003 ["simple" mode only] amount to add to the Y counter after each line -004 ["simple" mode only] amount to add to the X counter after each horizontal pixel -005 ["simple" mode only] amount to add to the Y counter after each horizontal pixel (0 = no rotation) -006 x------- -------- when set, register (line*4)+2 must be multiplied by 256 - -x------ -------- when set, registers 002 and 003 must be multiplied by 256 - --xxxxxx -------- clipping for the generated address? usually 3F, Premier Soccer - sets it to 07 before penalty kicks - -------- x------- when set, register (line*4)+3 must be multiplied by 256 - -------- -x------ when set, registers 004 and 005 must be multiplied by 256 - -------- --xxxxxx clipping for the generated address? usually 3F, Premier Soccer - sets it to 0F before penalty kicks -007 -------- -x------ enable "super" mode - -------- --x----- unknown (enable address clipping from register 006?) - -------- ---x---- unknown - -------- ------x- (not sure) enable clipping with registers 008-00b -008 min x screen coordinate to draw to (only when enabled by register 7) -009 max x screen coordinate to draw to (only when enabled by register 7) -00a min y screen coordinate to draw to (only when enabled by register 7) -00b max y screen coordinate to draw to (only when enabled by register 7) -00c unknown -00d unknown -00e unknown -00f unknown - -additional control from extra RAM: -(line*4)+0 X counter starting value / 256 (add to register 000) -(line*4)+1 Y counter starting value / 256 (add to register 001) -(line*4)+2 amount to add to the X counter after each horizontal pixel -(line*4)+3 amount to add to the Y counter after each horizontal pixel - -*/ - - - - -static void K053936_zoom_draw(int chip,uint16_t *ctrl,uint16_t *linectrl, screen_device &screen, bitmap_ind16 &bitmap,const rectangle &cliprect,tilemap_t *tmap,int flags,uint32_t priority, int glfgreat_hack) -{ - if (!tmap) - return; - - if (ctrl[0x07] & 0x0040) - { - uint32_t startx,starty; - int incxx,incxy; - rectangle my_clip; - int y,maxy; - - // Racin' Force will get to here if glfgreat_hack is enabled, and it ends - // up setting a maximum y value of '13', thus causing nothing to be drawn. - // It looks like the roz output should be flipped somehow as it seems to be - // displaying the wrong areas of the tilemap and is rendered upside down, - // although due to the additional post-processing the voxel renderer performs - // it's difficult to know what the output SHOULD be. (hold W in Racin' Force - // to see the chip output) - - if (((ctrl[0x07] & 0x0002) && ctrl[0x09]) && (glfgreat_hack)) /* wrong, but fixes glfgreat */ - { - my_clip.min_x = ctrl[0x08] + K053936_offset[chip][0]+2; - my_clip.max_x = ctrl[0x09] + K053936_offset[chip][0]+2 - 1; - if (my_clip.min_x < cliprect.min_x) - my_clip.min_x = cliprect.min_x; - if (my_clip.max_x > cliprect.max_x) - my_clip.max_x = cliprect.max_x; - - y = ctrl[0x0a] + K053936_offset[chip][1]-2; - if (y < cliprect.min_y) - y = cliprect.min_y; - maxy = ctrl[0x0b] + K053936_offset[chip][1]-2 - 1; - if (maxy > cliprect.max_y) - maxy = cliprect.max_y; - - } - else - { - my_clip.min_x = cliprect.min_x; - my_clip.max_x = cliprect.max_x; - - y = cliprect.min_y; - maxy = cliprect.max_y; - } - - while (y <= maxy) - { - uint16_t *lineaddr = linectrl + 4*((y - K053936_offset[chip][1]) & 0x1ff); - my_clip.min_y = my_clip.max_y = y; - - startx = 256 * (int16_t)(lineaddr[0] + ctrl[0x00]); - starty = 256 * (int16_t)(lineaddr[1] + ctrl[0x01]); - incxx = (int16_t)(lineaddr[2]); - incxy = (int16_t)(lineaddr[3]); - - if (ctrl[0x06] & 0x8000) incxx *= 256; - if (ctrl[0x06] & 0x0080) incxy *= 256; - - startx -= K053936_offset[chip][0] * incxx; - starty -= K053936_offset[chip][0] * incxy; - - tmap->draw_roz(screen, bitmap, my_clip, startx << 5,starty << 5, - incxx << 5,incxy << 5,0,0, - K053936_wraparound[chip], - flags,priority); - - y++; - } - } - else /* "simple" mode */ - { - uint32_t startx,starty; - int incxx,incxy,incyx,incyy; - - startx = 256 * (int16_t)(ctrl[0x00]); - starty = 256 * (int16_t)(ctrl[0x01]); - incyx = (int16_t)(ctrl[0x02]); - incyy = (int16_t)(ctrl[0x03]); - incxx = (int16_t)(ctrl[0x04]); - incxy = (int16_t)(ctrl[0x05]); - - if (ctrl[0x06] & 0x4000) { incyx *= 256; incyy *= 256; } - if (ctrl[0x06] & 0x0040) { incxx *= 256; incxy *= 256; } - - startx -= K053936_offset[chip][1] * incyx; - starty -= K053936_offset[chip][1] * incyy; - - startx -= K053936_offset[chip][0] * incxx; - starty -= K053936_offset[chip][0] * incxy; - - tmap->draw_roz(screen, bitmap, cliprect, startx << 5,starty << 5, - incxx << 5,incxy << 5,incyx << 5,incyy << 5, - K053936_wraparound[chip], - flags,priority); - } - -#if 0 -if (machine.input().code_pressed(KEYCODE_D)) - popmessage("%04x %04x %04x %04x\n%04x %04x %04x %04x\n%04x %04x %04x %04x\n%04x %04x %04x %04x", - ctrl[0x00], - ctrl[0x01], - ctrl[0x02], - ctrl[0x03], - ctrl[0x04], - ctrl[0x05], - ctrl[0x06], - ctrl[0x07], - ctrl[0x08], - ctrl[0x09], - ctrl[0x0a], - ctrl[0x0b], - ctrl[0x0c], - ctrl[0x0d], - ctrl[0x0e], - ctrl[0x0f]); -#endif -} - - -void K053936_0_zoom_draw(screen_device &screen, bitmap_ind16 &bitmap,const rectangle &cliprect,tilemap_t *tmap,int flags,uint32_t priority, int glfgreat_hack) -{ - uint16_t *ctrl = reinterpret_cast(tmap->machine().root_device().memshare("k053936_0_ctrl")->ptr()); - uint16_t *linectrl = reinterpret_cast(tmap->machine().root_device().memshare("k053936_0_line")->ptr()); - K053936_zoom_draw(0,ctrl,linectrl,screen,bitmap,cliprect,tmap,flags,priority, glfgreat_hack); -} - -void K053936_wraparound_enable(int chip, int status) -{ - K053936_wraparound[chip] = status; -} - - -void K053936_set_offset(int chip, int xoffs, int yoffs) -{ - K053936_offset[chip][0] = xoffs; - K053936_offset[chip][1] = yoffs; -} - - - - -/***************************************************************************/ -/* */ -/* 053936 */ -/* */ -/***************************************************************************/ - -DEFINE_DEVICE_TYPE(K053936, k053936_device, "k053936", "K053936 Video Controller") - -k053936_device::k053936_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : device_t(mconfig, K053936, tag, owner, clock), - m_ctrl(nullptr), - m_linectrl(nullptr), - m_wrap(0), - m_xoff(0), - m_yoff(0) -{ -} - -//------------------------------------------------- -// device_start - device-specific startup -//------------------------------------------------- - -void k053936_device::device_start() -{ - m_ctrl = make_unique_clear(0x20); - m_linectrl = make_unique_clear(0x4000); - - save_pointer(NAME(m_ctrl), 0x20); - save_pointer(NAME(m_linectrl), 0x4000); -} - -//------------------------------------------------- -// device_reset - device-specific reset -//------------------------------------------------- - -void k053936_device::device_reset() -{ - memset(m_ctrl.get(), 0, 0x20); -} - - -/***************************************************************************** - DEVICE HANDLERS -*****************************************************************************/ - -void k053936_device::ctrl_w(offs_t offset, uint16_t data, uint16_t mem_mask) -{ - COMBINE_DATA(&m_ctrl[offset]); -} - -uint16_t k053936_device::ctrl_r(offs_t offset) -{ - return m_ctrl[offset]; -} - -void k053936_device::linectrl_w(offs_t offset, uint16_t data, uint16_t mem_mask) -{ - COMBINE_DATA(&m_linectrl[offset]); -} - -uint16_t k053936_device::linectrl_r(offs_t offset) -{ - return m_linectrl[offset]; -} - -// there is another implementation of this in video/konamigx.c (!) -// why? shall they be merged? -void k053936_device::zoom_draw( screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int flags, uint32_t priority, int glfgreat_hack ) -{ - if (!tmap) - return; - - if (m_ctrl[0x07] & 0x0040) - { - uint32_t startx, starty; - int incxx, incxy; - rectangle my_clip; - int y, maxy; - - // Racin' Force will get to here if glfgreat_hack is enabled, and it ends - // up setting a maximum y value of '13', thus causing nothing to be drawn. - // It looks like the roz output should be flipped somehow as it seems to be - // displaying the wrong areas of the tilemap and is rendered upside down, - // although due to the additional post-processing the voxel renderer performs - // it's difficult to know what the output SHOULD be. (hold W in Racin' Force - // to see the chip output) - - if (((m_ctrl[0x07] & 0x0002) && m_ctrl[0x09]) && (glfgreat_hack)) /* wrong, but fixes glfgreat */ - { - my_clip.min_x = m_ctrl[0x08] + m_xoff + 2; - my_clip.max_x = m_ctrl[0x09] + m_xoff + 2 - 1; - if (my_clip.min_x < cliprect.min_x) - my_clip.min_x = cliprect.min_x; - if (my_clip.max_x > cliprect.max_x) - my_clip.max_x = cliprect.max_x; - - y = m_ctrl[0x0a] + m_yoff - 2; - if (y < cliprect.min_y) - y = cliprect.min_y; - maxy = m_ctrl[0x0b] + m_yoff - 2 - 1; - if (maxy > cliprect.max_y) - maxy = cliprect.max_y; - } - else - { - my_clip.min_x = cliprect.min_x; - my_clip.max_x = cliprect.max_x; - - y = cliprect.min_y; - maxy = cliprect.max_y; - } - - while (y <= maxy) - { - uint16_t *lineaddr = m_linectrl.get() + 4 * ((y - m_yoff) & 0x1ff); - - my_clip.min_y = my_clip.max_y = y; - - startx = 256 * (int16_t)(lineaddr[0] + m_ctrl[0x00]); - starty = 256 * (int16_t)(lineaddr[1] + m_ctrl[0x01]); - incxx = (int16_t)(lineaddr[2]); - incxy = (int16_t)(lineaddr[3]); - - if (m_ctrl[0x06] & 0x8000) - incxx *= 256; - - if (m_ctrl[0x06] & 0x0080) - incxy *= 256; - - startx -= m_xoff * incxx; - starty -= m_xoff * incxy; - - tmap->draw_roz(screen, bitmap, my_clip, startx << 5,starty << 5, - incxx << 5,incxy << 5,0,0, - m_wrap, - flags,priority); - - y++; - } - } - else /* "simple" mode */ - { - uint32_t startx, starty; - int incxx, incxy, incyx, incyy; - - startx = 256 * (int16_t)(m_ctrl[0x00]); - starty = 256 * (int16_t)(m_ctrl[0x01]); - incyx = (int16_t)(m_ctrl[0x02]); - incyy = (int16_t)(m_ctrl[0x03]); - incxx = (int16_t)(m_ctrl[0x04]); - incxy = (int16_t)(m_ctrl[0x05]); - - if (m_ctrl[0x06] & 0x4000) - { - incyx *= 256; - incyy *= 256; - } - - if (m_ctrl[0x06] & 0x0040) - { - incxx *= 256; - incxy *= 256; - } - - startx -= m_yoff * incyx; - starty -= m_yoff * incyy; - - startx -= m_xoff * incxx; - starty -= m_xoff * incxy; - - tmap->draw_roz(screen, bitmap, cliprect, startx << 5,starty << 5, - incxx << 5,incxy << 5,incyx << 5,incyy << 5, - m_wrap, - flags,priority); - } - -#if 0 -if (machine.input().code_pressed(KEYCODE_D)) - popmessage("%04x %04x %04x %04x\n%04x %04x %04x %04x\n%04x %04x %04x %04x\n%04x %04x %04x %04x", - m_ctrl[0x00], - m_ctrl[0x01], - m_ctrl[0x02], - m_ctrl[0x03], - m_ctrl[0x04], - m_ctrl[0x05], - m_ctrl[0x06], - m_ctrl[0x07], - m_ctrl[0x08], - m_ctrl[0x09], - m_ctrl[0x0a], - m_ctrl[0x0b], - m_ctrl[0x0c], - m_ctrl[0x0d], - m_ctrl[0x0e], - m_ctrl[0x0f]); -#endif -} - -void k053936_device::zoom_draw( screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int flags, uint32_t priority, int glfgreat_hack ) -{ - if (!tmap) - return; - - if (m_ctrl[0x07] & 0x0040) - { - uint32_t startx, starty; - int incxx, incxy; - rectangle my_clip; - int y, maxy; - - // Racin' Force will get to here if glfgreat_hack is enabled, and it ends - // up setting a maximum y value of '13', thus causing nothing to be drawn. - // It looks like the roz output should be flipped somehow as it seems to be - // displaying the wrong areas of the tilemap and is rendered upside down, - // although due to the additional post-processing the voxel renderer performs - // it's difficult to know what the output SHOULD be. (hold W in Racin' Force - // to see the chip output) - - if (((m_ctrl[0x07] & 0x0002) && m_ctrl[0x09]) && (glfgreat_hack)) /* wrong, but fixes glfgreat */ - { - my_clip.min_x = m_ctrl[0x08] + m_xoff + 2; - my_clip.max_x = m_ctrl[0x09] + m_xoff + 2 - 1; - if (my_clip.min_x < cliprect.min_x) - my_clip.min_x = cliprect.min_x; - if (my_clip.max_x > cliprect.max_x) - my_clip.max_x = cliprect.max_x; - - y = m_ctrl[0x0a] + m_yoff - 2; - if (y < cliprect.min_y) - y = cliprect.min_y; - maxy = m_ctrl[0x0b] + m_yoff - 2 - 1; - if (maxy > cliprect.max_y) - maxy = cliprect.max_y; - } - else - { - my_clip.min_x = cliprect.min_x; - my_clip.max_x = cliprect.max_x; - - y = cliprect.min_y; - maxy = cliprect.max_y; - } - - while (y <= maxy) - { - uint16_t *lineaddr = m_linectrl.get() + 4 * ((y - m_yoff) & 0x1ff); - - my_clip.min_y = my_clip.max_y = y; - - startx = 256 * (int16_t)(lineaddr[0] + m_ctrl[0x00]); - starty = 256 * (int16_t)(lineaddr[1] + m_ctrl[0x01]); - incxx = (int16_t)(lineaddr[2]); - incxy = (int16_t)(lineaddr[3]); - - if (m_ctrl[0x06] & 0x8000) - incxx *= 256; - - if (m_ctrl[0x06] & 0x0080) - incxy *= 256; - - startx -= m_xoff * incxx; - starty -= m_xoff * incxy; - - tmap->draw_roz(screen, bitmap, my_clip, startx << 5,starty << 5, - incxx << 5,incxy << 5,0,0, - m_wrap, - flags,priority); - - y++; - } - } - else /* "simple" mode */ - { - uint32_t startx, starty; - int incxx, incxy, incyx, incyy; - - startx = 256 * (int16_t)(m_ctrl[0x00]); - starty = 256 * (int16_t)(m_ctrl[0x01]); - incyx = (int16_t)(m_ctrl[0x02]); - incyy = (int16_t)(m_ctrl[0x03]); - incxx = (int16_t)(m_ctrl[0x04]); - incxy = (int16_t)(m_ctrl[0x05]); - - if (m_ctrl[0x06] & 0x4000) - { - incyx *= 256; - incyy *= 256; - } - - if (m_ctrl[0x06] & 0x0040) - { - incxx *= 256; - incxy *= 256; - } - - startx -= m_yoff * incyx; - starty -= m_yoff * incyy; - - startx -= m_xoff * incxx; - starty -= m_xoff * incxy; - - tmap->draw_roz(screen, bitmap, cliprect, startx << 5,starty << 5, - incxx << 5,incxy << 5,incyx << 5,incyy << 5, - m_wrap, - flags,priority); - } -} - - - - -void K053936GP_set_offset(int chip, int xoffs, int yoffs) { K053936_offset[chip][0] = xoffs; K053936_offset[chip][1] = yoffs; } - -void K053936GP_clip_enable(int chip, int status) { K053936_clip_enabled[chip] = status; } - -void K053936GP_set_cliprect(int chip, int minx, int maxx, int miny, int maxy) -{ - rectangle &cliprect = K053936_cliprect[chip]; - cliprect.set(minx, maxx, miny, maxy); -} - -static inline void K053936GP_copyroz32clip( running_machine &machine, - bitmap_rgb32 &dst_bitmap, bitmap_ind16 &src_bitmap, - const rectangle &dst_cliprect, const rectangle &src_cliprect, - uint32_t _startx,uint32_t _starty,int _incxx,int _incxy,int _incyx,int _incyy, - int tilebpp, int blend, int alpha, int clip, int pixeldouble_output, palette_device &palette ) -{ - static const int colormask[8]={1,3,7,0xf,0x1f,0x3f,0x7f,0xff}; - int cy, cx; - int ecx; - int src_pitch, incxy, incxx; - int src_minx, src_maxx, src_miny, src_maxy, cmask; - uint16_t *src_base; - size_t src_size; - - const pen_t *pal_base; - int dst_ptr; - int dst_size; - int dst_base2; - - int tx, dst_pitch; - uint32_t *dst_base; - int starty, incyy, startx, incyx, ty, sx, sy; - - incxy = _incxy; incxx = _incxx; incyy = _incyy; incyx = _incyx; - starty = _starty; startx = _startx; - - if (clip) // set source clip range to some extreme values when disabled - { - src_minx = src_cliprect.min_x; - src_maxx = src_cliprect.max_x; - src_miny = src_cliprect.min_y; - src_maxy = src_cliprect.max_y; - } - // this simply isn't safe to do! - else { src_minx = src_miny = -0x10000; src_maxx = src_maxy = 0x10000; } - - // set target clip range - sx = dst_cliprect.min_x; - tx = dst_cliprect.max_x - sx + 1; - sy = dst_cliprect.min_y; - ty = dst_cliprect.max_y - sy + 1; - - startx += sx * incxx + sy * incyx; - starty += sx * incxy + sy * incyy; - - // adjust entry points and other loop constants - dst_pitch = dst_bitmap.rowpixels(); - dst_base = &dst_bitmap.pix(0); - dst_base2 = sy * dst_pitch + sx + tx; - ecx = tx = -tx; - - tilebpp = (tilebpp-1) & 7; - pal_base = palette.pens(); - cmask = colormask[tilebpp]; - - src_pitch = src_bitmap.rowpixels(); - src_base = &src_bitmap.pix(0); - src_size = src_bitmap.width() * src_bitmap.height(); - dst_size = dst_bitmap.width() * dst_bitmap.height(); - dst_ptr = 0;//dst_base; - cy = starty; - cx = startx; - - if (blend > 0) - { - dst_ptr += dst_pitch; // draw blended - starty += incyy; - startx += incyx; - - do { - do { - int srcx = (cx >> 16) & 0x1fff; - int srcy = (cy >> 16) & 0x1fff; - int pixel; - uint32_t offs; - offs = srcy * src_pitch + srcx; - - cx += incxx; - cy += incxy; - - if (offs>=src_size) - continue; - - if (srcx < src_minx || srcx > src_maxx || srcy < src_miny || srcy > src_maxy) - continue; - - pixel = src_base[offs]; - if (!(pixel & cmask)) - continue; - - if ((dst_ptr+ecx+dst_base2)> 16) & 0x1fff; - int srcy = (cy >> 16) & 0x1fff; - int pixel; - uint32_t offs; - - offs = srcy * src_pitch + srcx; - - cx += incxx; - cy += incxy; - - if (offs>=src_size) - continue; - - if (srcx < src_minx || srcx > src_maxx || srcy < src_miny || srcy > src_maxy) - continue; - - pixel = src_base[offs]; - if (!(pixel & cmask)) - continue; - - - - if ((dst_ptr+ecx+dst_base2)pixmap(); - rectangle &src_cliprect = K053936_cliprect[chip]; - clip = K053936_clip_enabled[chip]; - - if (ctrl[0x07] & 0x0040) /* "super" mode */ - { - my_clip.min_x = cliprect.min_x; - my_clip.max_x = cliprect.max_x; - y = cliprect.min_y; - maxy = cliprect.max_y; - - while (y <= maxy) - { - lineaddr = linectrl + ( ((y - K053936_offset[chip][1]) & 0x1ff) << 2); - my_clip.min_y = my_clip.max_y = y; - - startx = (int16_t)(lineaddr[0] + ctrl[0x00]) << 8; - starty = (int16_t)(lineaddr[1] + ctrl[0x01]) << 8; - incxx = (int16_t)(lineaddr[2]); - incxy = (int16_t)(lineaddr[3]); - - if (ctrl[0x06] & 0x8000) incxx <<= 8; - if (ctrl[0x06] & 0x0080) incxy <<= 8; - - startx -= K053936_offset[chip][0] * incxx; - starty -= K053936_offset[chip][0] * incxy; - - K053936GP_copyroz32clip(machine, - bitmap, src_bitmap, my_clip, src_cliprect, - startx<<5, starty<<5, incxx<<5, incxy<<5, 0, 0, - tilebpp, blend, alpha, clip, pixeldouble_output, palette); - y++; - } - } - else /* "simple" mode */ - { - startx = (int16_t)(ctrl[0x00]) << 8; - starty = (int16_t)(ctrl[0x01]) << 8; - incyx = (int16_t)(ctrl[0x02]); - incyy = (int16_t)(ctrl[0x03]); - incxx = (int16_t)(ctrl[0x04]); - incxy = (int16_t)(ctrl[0x05]); - - if (ctrl[0x06] & 0x4000) { incyx <<= 8; incyy <<= 8; } - if (ctrl[0x06] & 0x0040) { incxx <<= 8; incxy <<= 8; } - - startx -= K053936_offset[chip][1] * incyx; - starty -= K053936_offset[chip][1] * incyy; - - startx -= K053936_offset[chip][0] * incxx; - starty -= K053936_offset[chip][0] * incxy; - - K053936GP_copyroz32clip(machine, - bitmap, src_bitmap, cliprect, src_cliprect, - startx<<5, starty<<5, incxx<<5, incxy<<5, incyx<<5, incyy<<5, - tilebpp, blend, alpha, clip, pixeldouble_output, palette); - } -} - -static void K053936GP_zoom_draw(running_machine &machine, - int chip, uint32_t *ctrl1, uint32_t *linectrl1, - bitmap_rgb32 &bitmap, const rectangle &cliprect, tilemap_t *tmap, - int tilebpp, int blend, int alpha, int pixeldouble_output, palette_device &palette) -{ - uint16_t *lineaddr; - - // Horrible but that's what the code previously did, only hidden - uint16_t *ctrl = (uint16_t *)ctrl1; - uint16_t *linectrl = (uint16_t *)linectrl1; - - rectangle my_clip; - uint32_t startx, starty; - int incxx, incxy, incyx, incyy, y, maxy, clip; - - bitmap_ind16 &src_bitmap = tmap->pixmap(); - rectangle &src_cliprect = K053936_cliprect[chip]; - clip = K053936_clip_enabled[chip]; - - if (ctrl[0x07] & 0x0040) /* "super" mode */ - { - my_clip.min_x = cliprect.min_x; - my_clip.max_x = cliprect.max_x; - y = cliprect.min_y; - maxy = cliprect.max_y; - - while (y <= maxy) - { - lineaddr = linectrl + ( ((y - K053936_offset[chip][1]) & 0x1ff) << 2); - my_clip.min_y = my_clip.max_y = y; - - startx = (int16_t)(lineaddr[0] + ctrl[0x00]) << 8; - starty = (int16_t)(lineaddr[1] + ctrl[0x01]) << 8; - incxx = (int16_t)(lineaddr[2]); - incxy = (int16_t)(lineaddr[3]); - - if (ctrl[0x06] & 0x8000) incxx <<= 8; - if (ctrl[0x06] & 0x0080) incxy <<= 8; - - startx -= K053936_offset[chip][0] * incxx; - starty -= K053936_offset[chip][0] * incxy; - - K053936GP_copyroz32clip(machine, - bitmap, src_bitmap, my_clip, src_cliprect, - startx<<5, starty<<5, incxx<<5, incxy<<5, 0, 0, - tilebpp, blend, alpha, clip, pixeldouble_output, palette); - y++; - } - } - else /* "simple" mode */ - { - startx = (int16_t)(ctrl[0x00]) << 8; - starty = (int16_t)(ctrl[0x01]) << 8; - incyx = (int16_t)(ctrl[0x02]); - incyy = (int16_t)(ctrl[0x03]); - incxx = (int16_t)(ctrl[0x04]); - incxy = (int16_t)(ctrl[0x05]); - - if (ctrl[0x06] & 0x4000) { incyx <<= 8; incyy <<= 8; } - if (ctrl[0x06] & 0x0040) { incxx <<= 8; incxy <<= 8; } - - startx -= K053936_offset[chip][1] * incyx; - starty -= K053936_offset[chip][1] * incyy; - - startx -= K053936_offset[chip][0] * incxx; - starty -= K053936_offset[chip][0] * incxy; - - K053936GP_copyroz32clip(machine, - bitmap, src_bitmap, cliprect, src_cliprect, - startx<<5, starty<<5, incxx<<5, incxy<<5, incyx<<5, incyy<<5, - tilebpp, blend, alpha, clip, pixeldouble_output, palette); - } -} - -void K053936GP_0_zoom_draw(running_machine &machine, bitmap_rgb32 &bitmap, const rectangle &cliprect, - tilemap_t *tmap, int tilebpp, int blend, int alpha, int pixeldouble_output, uint16_t* temp_m_k053936_0_ctrl_16, uint16_t* temp_m_k053936_0_linectrl_16,uint32_t* temp_m_k053936_0_ctrl, uint32_t* temp_m_k053936_0_linectrl, palette_device &palette) -{ - if (temp_m_k053936_0_ctrl_16) - { - K053936GP_zoom_draw(machine, 0,temp_m_k053936_0_ctrl_16,temp_m_k053936_0_linectrl_16,bitmap,cliprect,tmap,tilebpp,blend,alpha, pixeldouble_output, palette); - } - else - { - K053936GP_zoom_draw(machine, 0,temp_m_k053936_0_ctrl,temp_m_k053936_0_linectrl,bitmap,cliprect,tmap,tilebpp,blend,alpha, pixeldouble_output, palette); - } -} diff --git a/src/mame/shared/k053936.h b/src/mame/shared/k053936.h deleted file mode 100644 index 75894c2bf95..00000000000 --- a/src/mame/shared/k053936.h +++ /dev/null @@ -1,60 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:David Haywood -#ifndef MAME_VIDEO_K053936_H -#define MAME_VIDEO_K053936_H - -#pragma once - -#include "emupal.h" -#include "tilemap.h" - - -void K053936_0_zoom_draw(screen_device &screen, bitmap_ind16 &bitmap,const rectangle &cliprect,tilemap_t *tmap,int flags,uint32_t priority, int glfgreat_hack); -void K053936_wraparound_enable(int chip, int status); -void K053936_set_offset(int chip, int xoffs, int yoffs); - -// GX specific implementations... -void K053936GP_set_offset(int chip, int xoffs, int yoffs); -void K053936GP_clip_enable(int chip, int status); -void K053936GP_set_cliprect(int chip, int minx, int maxx, int miny, int maxy); -void K053936GP_0_zoom_draw(running_machine &machine, bitmap_rgb32 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int tilebpp, int blend, int alpha, int pixeldouble_output, uint16_t* temp_m_k053936_0_ctrl_16, uint16_t* temp_m_k053936_0_linectrl_16, uint32_t* temp_m_k053936_0_ctrl, uint32_t* temp_m_k053936_0_linectrl, palette_device &palette); - - -class k053936_device : public device_t -{ -public: - k053936_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - ~k053936_device() {} - - // configuration - void set_wrap(int wrap) { m_wrap = wrap; } - void set_offsets(int x_offset, int y_offset) - { - m_xoff = x_offset; - m_yoff = y_offset; - } - - void ctrl_w(offs_t offset, uint16_t data, uint16_t mem_mask = ~0); - uint16_t ctrl_r(offs_t offset); - void linectrl_w(offs_t offset, uint16_t data, uint16_t mem_mask = ~0); - uint16_t linectrl_r(offs_t offset); - void zoom_draw(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int flags, uint32_t priority, int glfgreat_hack); - void zoom_draw(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect, tilemap_t *tmap, int flags, uint32_t priority, int glfgreat_hack); - // void wraparound_enable(int status); unused? // shall we merge this into the configuration intf? - // void set_offset(int xoffs, int yoffs); unused? // shall we merge this into the configuration intf? - -protected: - // device-level overrides - virtual void device_start() override; - virtual void device_reset() override; - -private: - // internal state - std::unique_ptr m_ctrl; - std::unique_ptr m_linectrl; - int m_wrap, m_xoff, m_yoff; -}; - -DECLARE_DEVICE_TYPE(K053936, k053936_device) - -#endif // MAME_VIDEO_K053936_H diff --git a/src/mame/shared/mc8123.cpp b/src/mame/shared/mc8123.cpp deleted file mode 100644 index 33acc77b096..00000000000 --- a/src/mame/shared/mc8123.cpp +++ /dev/null @@ -1,416 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Nicola Salmoria, David Widel -/*************************************************************************** - -NEC MC-8123 encryption emulation - -Decryption tables provided by David Widel -Decryption algorithm by Nicola Salmoria - -The NEC MC-8123 is a Z80 with built-in encryption. -It contains 0x2000 bytes of battery-backed RAM, when the battery dies the -game stops working. It's possible that the CPU would work as a normal Z80 -in that case, this hasn't been verified. - -When the CPU reads a byte from memory, it uses 12 bits of the address and -the information of whether the byte is an opcode or not to select a byte in -the internal RAM. The byte controls how the decryption works. - -A special value in the internal RAM instructs the CPU to not apply the decryption -algorithm at all. This is necessary for the CPU to be able to use RAM areas -normally. - -In theory, the size of the key would make the encryption quite secure. - -In practice, the contents of the internal RAM were generated using a linear -congruential generator, so the whole key can be generated starting from a single -24-bit seed. - -The LCG is the same that was used to generate the FD1094 keys. -Note that the algorithm skips the special value that would instruct the CPU to -not decrypt at that address. - -void generate_key(uint8_t (&key)[0x2000], uint32_t seed, unsigned upper_bound) -{ - unsigned i; - - for (i = 0; i < upper_bound; ++i) - { - uint8_t byteval; - - do - { - seed *= 0x29; - seed += seed << 16; - - byteval = (~seed >> 16) & 0xff; - } - while (byteval == 0xff); - - key[i] = byteval; - } - - for ( ; i < 0x2000; ++i) - key[i] = 0xff; -} - - -The known games that use this CPU are: - -CPU # Game Notes Seed Upper Limit --------- ------------------------- ------------------ ------ ----- -317-0029 Block Gal NEC MC-8123B 651 091755 1800? -317-0030 Perfect Billiard 9451EC 1C00 -317-0040 Toki no Senshi - Chrono Soldier 068713 1c00 -317-0042 Opa Opa B31FD0 1C00 -317-0043 Wonder Boy Monster Land 640708 1C00 -317-0054 Shinobi (sound CPU) NEC MC-8123B 652 088992 1800 -317-0057 Fantasy Zone 2 ADFACE 1800 -317-0064 Ufo Senshi Yohko Chan 880603 1C00 -317-0066 Altered Beast (sound CPU) NEC MC-8123B 704 ED8600 1800 -317-5002 Gigas 1 & 2 NEC MC-8123 638 234567 1C00 -317-5004 Eagle Writer Not Dumped -317-5005 Astro Flash Not Dumped -317-5008 Perfect Billiard 9451EC 1C00 -317-5012 Ganbare Chinsan Ooshoubu NEC MC-8123A 804B54 1C00 -317-5014 DakkoChan Jansoh NEC MC-8123B 206850 1C00 -317-5??? Ninja Kid II (sound CPU) NEC MC-8123A 646 27998D 1800 -317-???? Center Court (sound CPU) NEC MC-8123B 703 640506 1800 -317-???? Omega 861226 1C00? - -***************************************************************************/ - -#include "emu.h" -#include "mc8123.h" - - -DEFINE_DEVICE_TYPE(MC8123, mc8123_device, "mc8123", "MC-8123") - -//------------------------------------------------- -// mc8123_device - constructor -//------------------------------------------------- - -mc8123_device::mc8123_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) - : z80_device(mconfig, MC8123, tag, owner, clock) - , m_key(*this, "key") -{ -} - - -namespace { - -template constexpr u8 BITS(T b) { return u8(1) << b; } -template constexpr u8 BITS(T b, U... c) { return (u8(1) << b) | BITS(c...); } - -} // anonymous namespace - -u8 mc8123_device::decrypt_type0(u8 val, u8 param, unsigned swap) -{ - if (swap == 0) val = bitswap<8>(val,7,5,3,1,2,0,6,4); - if (swap == 1) val = bitswap<8>(val,5,3,7,2,1,0,4,6); - if (swap == 2) val = bitswap<8>(val,0,3,4,6,7,1,5,2); - if (swap == 3) val = bitswap<8>(val,0,7,3,2,6,4,1,5); - - if (BIT(param,3) && BIT(val,7)) - val ^= BITS(5,3,0); - - if (BIT(param,2) && BIT(val,6)) - val ^= BITS(7,2,1); - - if (BIT(val,6)) val ^= BITS(7); - - if (BIT(param,1) && BIT(val,7)) - val ^= BITS(6); - - if (BIT(val,2)) val ^= BITS(5,0); - - val ^= BITS(4,3,1); - - if (BIT(param,2)) val ^= BITS(5,2,0); - if (BIT(param,1)) val ^= BITS(7,6); - if (BIT(param,0)) val ^= BITS(5,0); - - if (BIT(param,0)) val = bitswap<8>(val,7,6,5,1,4,3,2,0); - - return val; -} - - -u8 mc8123_device::decrypt_type1a(u8 val, u8 param, unsigned swap) -{ - if (swap == 0) val = bitswap<8>(val,4,2,6,5,3,7,1,0); - if (swap == 1) val = bitswap<8>(val,6,0,5,4,3,2,1,7); - if (swap == 2) val = bitswap<8>(val,2,3,6,1,4,0,7,5); - if (swap == 3) val = bitswap<8>(val,6,5,1,3,2,7,0,4); - - if (BIT(param,2)) val = bitswap<8>(val,7,6,1,5,3,2,4,0); - - if (BIT(val,1)) val ^= BITS(0); - if (BIT(val,6)) val ^= BITS(3); - if (BIT(val,7)) val ^= BITS(6,3); - if (BIT(val,2)) val ^= BITS(6,3,1); - if (BIT(val,4)) val ^= BITS(7,6,2); - - if (BIT(val,7) ^ BIT(val,2)) - val ^= BITS(4); - - val ^= BITS(6,3,1,0); - - if (BIT(param,3)) val ^= BITS(7,2); - if (BIT(param,1)) val ^= BITS(6,3); - - if (BIT(param,0)) val = bitswap<8>(val,7,6,1,4,3,2,5,0); - - return val; -} - -u8 mc8123_device::decrypt_type1b(u8 val, u8 param, unsigned swap) -{ - if (swap == 0) val = bitswap<8>(val,1,0,3,2,5,6,4,7); - if (swap == 1) val = bitswap<8>(val,2,0,5,1,7,4,6,3); - if (swap == 2) val = bitswap<8>(val,6,4,7,2,0,5,1,3); - if (swap == 3) val = bitswap<8>(val,7,1,3,6,0,2,5,4); - - if (BIT(val,2) && BIT(val,0)) - val ^= BITS(7,4); - - if (BIT(val,7)) val ^= BITS(2); - if (BIT(val,5)) val ^= BITS(7,2); - if (BIT(val,1)) val ^= BITS(5); - if (BIT(val,6)) val ^= BITS(1); - if (BIT(val,4)) val ^= BITS(6,5); - if (BIT(val,0)) val ^= BITS(6,2,1); - if (BIT(val,3)) val ^= BITS(7,6,2,1,0); - - val ^= BITS(6,4,0); - - if (BIT(param,3)) val ^= BITS(4,1); - if (BIT(param,2)) val ^= BITS(7,6,3,0); - if (BIT(param,1)) val ^= BITS(4,3); - if (BIT(param,0)) val ^= BITS(6,2,1,0); - - return val; -} - -u8 mc8123_device::decrypt_type2a(u8 val, u8 param, unsigned swap) -{ - if (swap == 0) val = bitswap<8>(val,0,1,4,3,5,6,2,7); - if (swap == 1) val = bitswap<8>(val,6,3,0,5,7,4,1,2); - if (swap == 2) val = bitswap<8>(val,1,6,4,5,0,3,7,2); - if (swap == 3) val = bitswap<8>(val,4,6,7,5,2,3,1,0); - - if (BIT(val,3) || (BIT(param,1) && BIT(val,2))) - val = bitswap<8>(val,6,0,7,4,3,2,1,5); - - if (BIT(val,5)) val ^= BITS(7); - if (BIT(val,6)) val ^= BITS(5); - if (BIT(val,0)) val ^= BITS(6); - if (BIT(val,4)) val ^= BITS(3,0); - if (BIT(val,1)) val ^= BITS(2); - - val ^= BITS(7,6,5,4,1); - - if (BIT(param,2)) val ^= BITS(4,3,2,1,0); - - if (BIT(param,3)) - { - if (BIT(param,0)) - val = bitswap<8>(val,7,6,5,3,4,1,2,0); - else - val = bitswap<8>(val,7,6,5,1,2,4,3,0); - } - else if (BIT(param,0)) - { - val = bitswap<8>(val,7,6,5,2,1,3,4,0); - } - - return val; -} - -u8 mc8123_device::decrypt_type2b(u8 val, u8 param, unsigned swap) -{ - // only 0x20 possible encryptions for this method - all others have 0x40 - // this happens because BIT(param,2) cancels the other three - - if (swap == 0) val = bitswap<8>(val,1,3,4,6,5,7,0,2); - if (swap == 1) val = bitswap<8>(val,0,1,5,4,7,3,2,6); - if (swap == 2) val = bitswap<8>(val,3,5,4,1,6,2,0,7); - if (swap == 3) val = bitswap<8>(val,5,2,3,0,4,7,6,1); - - if (BIT(val,7) && BIT(val,3)) - val ^= BITS(6,4,0); - - if (BIT(val,7)) val ^= BITS(2); - if (BIT(val,5)) val ^= BITS(7,3); - if (BIT(val,1)) val ^= BITS(5); - if (BIT(val,4)) val ^= BITS(7,5,3,1); - - if (BIT(val,7) && BIT(val,5)) - val ^= BITS(4,0); - - if (BIT(val,5) && BIT(val,1)) - val ^= BITS(4,0); - - if (BIT(val,6)) val ^= BITS(7,5); - if (BIT(val,3)) val ^= BITS(7,6,5,1); - if (BIT(val,2)) val ^= BITS(3,1); - - val ^= BITS(7,3,2,1); - - if (BIT(param,3)) val ^= BITS(6,3,1); - if (BIT(param,2)) val ^= BITS(7,6,5,3,2,1); // same as the other three combined - if (BIT(param,1)) val ^= BITS(7); - if (BIT(param,0)) val ^= BITS(5,2); - - return val; -} - -u8 mc8123_device::decrypt_type3a(u8 val, u8 param, unsigned swap) -{ - if (swap == 0) val = bitswap<8>(val,5,3,1,7,0,2,6,4); - if (swap == 1) val = bitswap<8>(val,3,1,2,5,4,7,0,6); - if (swap == 2) val = bitswap<8>(val,5,6,1,2,7,0,4,3); - if (swap == 3) val = bitswap<8>(val,5,6,7,0,4,2,1,3); - - if (BIT(val,2)) val ^= BITS(7,5,4); - if (BIT(val,3)) val ^= BITS(0); - - if (BIT(param,0)) val = bitswap<8>(val,7,2,5,4,3,1,0,6); - - if (BIT(val,1)) val ^= BITS(6,0); - if (BIT(val,3)) val ^= BITS(4,2,1); - - if (BIT(param,3)) val ^= BITS(4,3); - - if (BIT(val,3)) val = bitswap<8>(val,5,6,7,4,3,2,1,0); - - if (BIT(val,5)) val ^= BITS(2,1); - - val ^= BITS(6,5,4,3); - - if (BIT(param,2)) val ^= BITS(7); - if (BIT(param,1)) val ^= BITS(4); - if (BIT(param,0)) val ^= BITS(0); - - return val; -} - -u8 mc8123_device::decrypt_type3b(u8 val, u8 param, unsigned swap) -{ - if (swap == 0) val = bitswap<8>(val,3,7,5,4,0,6,2,1); - if (swap == 1) val = bitswap<8>(val,7,5,4,6,1,2,0,3); - if (swap == 2) val = bitswap<8>(val,7,4,3,0,5,1,6,2); - if (swap == 3) val = bitswap<8>(val,2,6,4,1,3,7,0,5); - - if (BIT(val,2)) val ^= BITS(7); - - if (BIT(val,7)) val = bitswap<8>(val,7,6,3,4,5,2,1,0); - - if (BIT(param,3)) val ^= BITS(7); - - if (BIT(val,4)) val ^= BITS(6); - if (BIT(val,1)) val ^= BITS(6,4,2); - - if (BIT(val,7) && BIT(val,6)) - val ^= BITS(1); - - if (BIT(val,7)) val ^= BITS(1); - - if (BIT(param,3)) val ^= BITS(7); - if (BIT(param,2)) val ^= BITS(0); - - if (BIT(param,3)) val = bitswap<8>(val,4,6,3,2,5,0,1,7); - - if (BIT(val,4)) val ^= BITS(1); - if (BIT(val,5)) val ^= BITS(4); - if (BIT(val,7)) val ^= BITS(2); - - val ^= BITS(5,3,2); - - if (BIT(param,1)) val ^= BITS(7); - if (BIT(param,0)) val ^= BITS(3); - - return val; -} - -u8 mc8123_device::decrypt_internal(u8 val, u8 key, bool opcode) -{ - unsigned type = 0; - unsigned swap = 0; - u8 param = 0; - - key ^= 0xff; - - // no encryption - if (key == 0x00) - return val; - - type ^= BIT(key,0) << 0; - type ^= BIT(key,2) << 0; - type ^= BIT(key,0) << 1; - type ^= BIT(key,1) << 1; - type ^= BIT(key,2) << 1; - type ^= BIT(key,4) << 1; - type ^= BIT(key,4) << 2; - type ^= BIT(key,5) << 2; - - swap ^= BIT(key,0) << 0; - swap ^= BIT(key,1) << 0; - swap ^= BIT(key,2) << 1; - swap ^= BIT(key,3) << 1; - - param ^= BIT(key,0) << 0; - param ^= BIT(key,0) << 1; - param ^= BIT(key,2) << 1; - param ^= BIT(key,3) << 1; - param ^= BIT(key,0) << 2; - param ^= BIT(key,1) << 2; - param ^= BIT(key,6) << 2; - param ^= BIT(key,1) << 3; - param ^= BIT(key,6) << 3; - param ^= BIT(key,7) << 3; - - if (!opcode) - { - param ^= BITS(0); - type ^= BITS(0); - } - - switch (type) - { - default: - case 0: return decrypt_type0(val, param, swap); - case 1: return decrypt_type0(val, param, swap); - case 2: return decrypt_type1a(val, param, swap); - case 3: return decrypt_type1b(val, param, swap); - case 4: return decrypt_type2a(val, param, swap); - case 5: return decrypt_type2b(val, param, swap); - case 6: return decrypt_type3a(val, param, swap); - case 7: return decrypt_type3b(val, param, swap); - } -} - - -u8 mc8123_device::decrypt(offs_t addr, u8 val, bool opcode) -{ - // pick the translation table from bits fd57 of the address - offs_t const tbl_num = bitswap<12>(addr,15,14,13,12,11,10,8,6,4,2,1,0); - - return decrypt_internal(val, m_key[tbl_num | (opcode ? 0x0000 : 0x1000)], opcode); -} - - -void mc8123_device::decode(u8 *rom, u8 *opcodes, unsigned length) -{ - for (unsigned i = 0; i < length; i++) - { - unsigned const adr = (i >= 0xc000) ? ((i & 0x3fff) | 0x8000) : i; - u8 const src = rom[i]; - - // decode the opcodes - opcodes[i] = decrypt(adr, src, true); - - // decode the data - rom[i] = decrypt(adr, src, false); - } -} diff --git a/src/mame/shared/mc8123.h b/src/mame/shared/mc8123.h deleted file mode 100644 index 7871c1488ce..00000000000 --- a/src/mame/shared/mc8123.h +++ /dev/null @@ -1,43 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Nicola Salmoria, David Widel -/*************************************************************************** - - NEC MC-8123 encryption emulation - -***************************************************************************/ - -#ifndef MAME_MACHINE_MC8123 -#define MAME_MACHINE_MC8123 - -#pragma once - -#include "cpu/z80/z80.h" - -class mc8123_device : public z80_device -{ -public: - // construction/destruction - mc8123_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); - - // this function assumes a fixed portion of ROM at 0000-7FFF, and - // an arbitrary amount of banks at 8000-BFFF. - void decode(u8 *rom, u8 *opcodes, unsigned length); - -private: - static u8 decrypt_type0(u8 val, u8 param, unsigned swap); - static u8 decrypt_type1a(u8 val, u8 param, unsigned swap); - static u8 decrypt_type1b(u8 val, u8 param, unsigned swap); - static u8 decrypt_type2a(u8 val, u8 param, unsigned swap); - static u8 decrypt_type2b(u8 val, u8 param, unsigned swap); - static u8 decrypt_type3a(u8 val, u8 param, unsigned swap); - static u8 decrypt_type3b(u8 val, u8 param, unsigned swap); - static u8 decrypt_internal(u8 val, u8 key, bool opcode); - - u8 decrypt(offs_t addr, u8 val, bool opcode); - - required_region_ptr m_key; -}; - -DECLARE_DEVICE_TYPE(MC8123, mc8123_device) - -#endif // MAME_MACHINE_MC8123 diff --git a/src/mame/shared/nmk112.cpp b/src/mame/shared/nmk112.cpp deleted file mode 100644 index 4de5062ac14..00000000000 --- a/src/mame/shared/nmk112.cpp +++ /dev/null @@ -1,103 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Alex W. Jackson -/* NMK112 - NMK custom IC for bankswitching the sample ROMs of a pair of - OKI6295 ADPCM chips - - The address space of each OKI6295 is divided into four banks, each one - independently controlled. The sample table at the beginning of the - address space may be divided in four pages as well, banked together - with the sample data. This allows each of the four voices on the chip - to play a sample from a different bank at the same time. */ - -#include "emu.h" -#include "nmk112.h" - -#define TABLESIZE 0x100 -#define BANKSIZE 0x10000 - - - -DEFINE_DEVICE_TYPE(NMK112, nmk112_device, "nmk112", "NMK112") - -nmk112_device::nmk112_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : device_t(mconfig, NMK112, tag, owner, clock) - , m_page_mask(0xff) - , m_rom0(*this, finder_base::DUMMY_TAG) - , m_rom1(*this, finder_base::DUMMY_TAG) - , m_size0(0) - , m_size1(0) -{ -} - -//------------------------------------------------- -// device_start - device-specific startup -//------------------------------------------------- - -void nmk112_device::device_start() -{ - save_item(NAME(m_current_bank)); - - if (m_rom0) - m_size0 = m_rom0.bytes() - 0x40000; - - if (m_rom1) - m_size1 = m_rom1.bytes() - 0x40000; -} - -//------------------------------------------------- -// device_reset - device-specific reset -//------------------------------------------------- - -void nmk112_device::device_reset() -{ - for (int i = 0; i < 8; i++) - { - m_current_bank[i] = 0; - do_bankswitch(i, m_current_bank[i]); - } -} - -void nmk112_device::do_bankswitch( int offset, int data ) -{ - int chip = (offset & 4) >> 2; - int banknum = offset & 3; - int paged = (m_page_mask & (1 << chip)); - - uint8_t *rom = chip ? m_rom1 : m_rom0; - int size = chip ? m_size1 : m_size0; - - m_current_bank[offset] = data; - - if (size == 0) return; - - int bankaddr = (data * BANKSIZE) % size; - - /* copy the samples */ - if ((paged) && (banknum == 0)) - memcpy(rom + 0x400, rom + 0x40000 + bankaddr + 0x400, BANKSIZE - 0x400); - else - memcpy(rom + banknum * BANKSIZE, rom + 0x40000 + bankaddr, BANKSIZE); - - /* also copy the sample address table, if it is paged on this chip */ - if (paged) - { - rom += banknum * TABLESIZE; - memcpy(rom, rom + 0x40000 + bankaddr, TABLESIZE); - } -} - -/***************************************************************************** - DEVICE HANDLERS -*****************************************************************************/ - -void nmk112_device::okibank_w(offs_t offset, u8 data) -{ - if (m_current_bank[offset] != data) - do_bankswitch(offset, data); -} - -void nmk112_device::device_post_load() -{ - for (int i = 0; i < 8; i++) - do_bankswitch(i, m_current_bank[i]); -} diff --git a/src/mame/shared/nmk112.h b/src/mame/shared/nmk112.h deleted file mode 100644 index 5535d94899b..00000000000 --- a/src/mame/shared/nmk112.h +++ /dev/null @@ -1,53 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Alex W. Jackson -/************************************************************************* - - nmk112.h - -**************************************************************************/ - -#ifndef MAME_MACHINE_NMK112_H -#define MAME_MACHINE_NMK112_H - -#pragma once - -/*************************************************************************** - TYPE DEFINITIONS -***************************************************************************/ - -class nmk112_device : public device_t -{ -public: - nmk112_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - - // configuration - template nmk112_device &set_rom0_tag(T &&tag) { m_rom0.set_tag(std::forward(tag)); return *this; } - template nmk112_device &set_rom1_tag(T &&tag) { m_rom1.set_tag(std::forward(tag)); return *this; } - nmk112_device &set_page_mask(uint8_t mask) { m_page_mask = ~mask; return *this; } - - void okibank_w(offs_t offset, u8 data); - -protected: - // device-level overrides - virtual void device_start() override; - virtual void device_reset() override; - virtual void device_post_load() override; - -private: - void do_bankswitch( int offset, int data ); - - // internal state - - /* which chips have their sample address table divided into pages */ - uint8_t m_page_mask; - - uint8_t m_current_bank[8]; - - optional_region_ptr m_rom0, m_rom1; - int m_size0, m_size1; -}; - -DECLARE_DEVICE_TYPE(NMK112, nmk112_device) - - -#endif // MAME_MACHINE_NMK112_H diff --git a/src/mame/shared/tmap038.cpp b/src/mame/shared/tmap038.cpp deleted file mode 100644 index 9b007e28a2c..00000000000 --- a/src/mame/shared/tmap038.cpp +++ /dev/null @@ -1,263 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Luca Elia, Paul Priest, David Haywood -/* 038 Tilemap generator manufactured by NEC */ - -/* - [ Scrolling Layers ] - - Each 038 chip generates 1 layer. Up to 4 chips are used - (4 layers) - - Layer Size: 512 x 512 - Tiles: 8 x 8 & 16 x 16. - - There are 2 tilemaps in memory, one per tiles dimension. - A bit decides which one gets displayed. - The tiles depth varies with games, from 16 to 256 colors. - - A per layer row-scroll / row-select effect can be enabled: - - a different scroll value is fetched (from tile RAM) for each - scan line, and a different tilemap line for each scan line - - - -*************************************************************************** - - Callbacks for the TileMap code - - [ Tiles Format ] - - Offset: Bits: Value: - - 0.w fe-- ---- ---- --- Priority - --dc ba98 ---- ---- Color - ---- ---- 7654 3210 - - 2.w Code - - - When a row-scroll / row-select effect is enabled, the scroll values are - fetched starting from tile RAM + $1000, 4 bytes per scan line: - - Offset: Value: - - 0.w Tilemap line to display - 2.w X Scroll value - -*************************************************************************** - -*************************************************************************** - - Layers Registers - - - Offset: Bits: Value: - - 0.w f--- ---- ---- ---- 0 = Layer Flip X - -e-- ---- ---- ---- Activate Row-scroll - --d- ---- ---- ---- - ---c ba9- ---- ---- - ---- ---8 7654 3210 Scroll X - - 2.w f--- ---- ---- ---- 0 = Layer Flip Y - -e-- ---- ---- ---- Activate Row-select - --d- ---- ---- ---- 0 = 8x8 tiles, 1 = 16x16 tiles - ---c ba9- ---- ---- - ---- ---8 7654 3210 Scroll Y - - 4.w fedc ba98 765- ---- - ---- ---- ---4 ---- Layer Disable - ---- ---- ---- 3210 Varies* - - *color bank for mcatadv or Layer-Layer priority for cave - -There are more! - -*************************************************************************** - -TODO: - de-fragmentation and merge drawing behavior into tmap038.cpp - -*************************************************************************** - -*/ - -#include "emu.h" -#include "tmap038.h" - -void tilemap038_device::vram_map(address_map &map) -{ - map(0x0000, 0x0fff).rw(FUNC(tilemap038_device::vram_16x16_r), FUNC(tilemap038_device::vram_16x16_w)).share("vram_16x16"); - map(0x1000, 0x17ff).rw(FUNC(tilemap038_device::lineram_r), FUNC(tilemap038_device::lineram_w)).share("lineram"); - map(0x1800, 0x3fff).ram().share("scratchpad"); // scratchpad? - map(0x4000, 0x7fff).rw(FUNC(tilemap038_device::vram_8x8_r), FUNC(tilemap038_device::vram_8x8_w)).share("vram_8x8"); -} - -void tilemap038_device::vram_writeonly_map(address_map &map) -{ - map(0x0000, 0x0fff).w(FUNC(tilemap038_device::vram_16x16_w)).share("vram_16x16"); - map(0x1000, 0x17ff).w(FUNC(tilemap038_device::lineram_w)).share("lineram"); - map(0x1800, 0x3fff).writeonly().share("scratchpad"); // scratchpad? - map(0x4000, 0x7fff).w(FUNC(tilemap038_device::vram_8x8_w)).share("vram_8x8"); -} - -void tilemap038_device::vram_16x16_map(address_map &map) -{ - map(0x0000, 0x0fff).rw(FUNC(tilemap038_device::vram_16x16_r), FUNC(tilemap038_device::vram_16x16_w)).share("vram_16x16"); - map(0x1000, 0x17ff).rw(FUNC(tilemap038_device::lineram_r), FUNC(tilemap038_device::lineram_w)).share("lineram"); - map(0x1800, 0x3fff).ram().share("scratchpad"); // scratchpad? -} - -void tilemap038_device::vram_16x16_writeonly_map(address_map &map) -{ - map(0x0000, 0x0fff).w(FUNC(tilemap038_device::vram_16x16_w)).share("vram_16x16"); - map(0x1000, 0x17ff).w(FUNC(tilemap038_device::lineram_w)).share("lineram"); - map(0x1800, 0x3fff).writeonly().share("scratchpad"); // scratchpad? -} - -/* Some games, that only ever use the 8x8 tiles and no line scroll, - use mirror ram. For example in donpachi, writes to 400000-403fff - and 408000-407fff both go to the 8x8 tilemap ram. Use this function - in this cases. Note that the get_tile_info function looks in the - 4000-7fff range for tiles, so we have to write the data there. */ -void tilemap038_device::vram_8x8_map(address_map &map) -{ - map(0x0000, 0x3fff).rw(FUNC(tilemap038_device::vram_8x8_r), FUNC(tilemap038_device::vram_8x8_w)).share("vram_8x8"); -} - -DEFINE_DEVICE_TYPE(TMAP038, tilemap038_device, "tmap038", "038 Tilemap generator") - -tilemap038_device::tilemap038_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) - : device_t(mconfig, TMAP038, tag, owner, clock) - , m_vram_8x8(*this, "vram_8x8") - , m_vram_16x16(*this, "vram_16x16") - , m_lineram(*this, "lineram") - , m_vregs(nullptr) - , m_tiledim(false) - , m_gfxdecode(*this, finder_base::DUMMY_TAG) - , m_gfxno(0) - , m_038_cb(*this) - , m_xoffs(0) - , m_flipped_xoffs(0) - , m_yoffs(0) - , m_flipped_yoffs(0) -{ -} - -TILE_GET_INFO_MEMBER(tilemap038_device::get_tile_info) -{ - u32 tile, code = 0, color = 0, pri = 0; - - if (tile_is_16x16()) - { - tile = (tile_index % (512 / 8)) / 2 + ((tile_index / (512 / 8)) / 2) * (512 / 16); - tile = (m_vram_16x16 != nullptr) ? ((m_vram_16x16[tile * 2] << 16) + m_vram_16x16[(tile * 2) + 1]) : 0; - - color = (tile & 0x3f000000) >> (32 - 8); - pri = (tile & 0xc0000000) >> (32 - 2); - code = (tile & 0x0000ffff) * 4; - - code ^= tile_index & 1; - code ^= ((tile_index / (512 / 8)) & 1) * 2; - - if (!m_038_cb.isnull()) - m_038_cb(true, color, pri, code); - } - else if (tile_is_8x8()) - { - tile = (m_vram_8x8 != nullptr) ? ((m_vram_8x8[tile_index * 2] << 16) + m_vram_8x8[(tile_index * 2) + 1]) : 0; - - color = (tile & 0x3f000000) >> (32 - 8); - pri = (tile & 0xc0000000) >> (32 - 2); - code = (tile & 0x0003ffff); - - if (!m_038_cb.isnull()) - m_038_cb(false, color, pri, code); - } - - tileinfo.set(m_gfxno, code, color, 0); - tileinfo.category = pri; -} - - -void tilemap038_device::device_start() -{ - m_038_cb.resolve(); - m_vregs = make_unique_clear(0x6/2); - - if (m_vram_16x16 == nullptr && m_vram_8x8 == nullptr) - fatalerror("Tilemap 038 %s: VRAM not found",this->tag()); - - m_tmap = &machine().tilemap().create( - *m_gfxdecode, - tilemap_get_info_delegate(*this, FUNC(tilemap038_device::get_tile_info)), - TILEMAP_SCAN_ROWS, - 8,8, 512 / 8,512 / 8); - - m_tmap->set_transparent_pen(0); - - set_scroll_rows(1); // Initialize scroll rows - set_scroll_cols(1); // Initialize scroll cols - - save_item(NAME(m_tiledim)); - save_pointer(NAME(m_vregs), 0x6/2); -} - -void tilemap038_device::device_reset() -{ -} - -u16 tilemap038_device::vram_8x8_r(offs_t offset) -{ - return m_vram_8x8[offset]; -} - -void tilemap038_device::vram_8x8_w(offs_t offset, u16 data, u16 mem_mask) -{ - COMBINE_DATA(&m_vram_8x8[offset]); - if (tile_is_8x8()) - m_tmap->mark_tile_dirty(offset >> 1); -} - -u16 tilemap038_device::vram_16x16_r(offs_t offset) -{ - return m_vram_16x16[offset]; -} - -void tilemap038_device::vram_16x16_w(offs_t offset, u16 data, u16 mem_mask) -{ - COMBINE_DATA(&m_vram_16x16[offset]); - if (tile_is_16x16()) - { - offset >>= 1; - offset = (offset % (512 / 16)) * 2 + (offset / (512 / 16)) * (512 / 8) * 2; - m_tmap->mark_tile_dirty(offset + 0); - m_tmap->mark_tile_dirty(offset + 1); - m_tmap->mark_tile_dirty(offset + 0 + 512 / 8); - m_tmap->mark_tile_dirty(offset + 1 + 512 / 8); - } -} - -void tilemap038_device::prepare() -{ - // refresh tile size - if (m_vram_8x8 != nullptr && m_vram_16x16 != nullptr) - { - const bool new_tiledim = BIT(m_vregs[1], 13); - if (m_tiledim != new_tiledim) - { - m_tmap->mark_all_dirty(); - m_tiledim = new_tiledim; - } - } -} - -void tilemap038_device::draw(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, u32 flags, u8 pri, u8 pri_mask) { draw_common(screen, bitmap, cliprect, flags, pri, pri_mask); } -void tilemap038_device::draw(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect, u32 flags, u8 pri, u8 pri_mask) { draw_common(screen, bitmap, cliprect, flags, pri, pri_mask); } - -template -void tilemap038_device::draw_common(screen_device &screen, BitmapClass &bitmap, const rectangle &cliprect, u32 flags, u8 pri, u8 pri_mask) -{ - m_tmap->draw(screen, bitmap, cliprect, flags, pri, pri_mask); -} diff --git a/src/mame/shared/tmap038.h b/src/mame/shared/tmap038.h deleted file mode 100644 index cc5ba89813d..00000000000 --- a/src/mame/shared/tmap038.h +++ /dev/null @@ -1,114 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Luca Elia, Paul Priest, David Haywood -#ifndef MAME_VIDEO_TMAP038_H -#define MAME_VIDEO_TMAP038_H - -#pragma once - -#include "tilemap.h" - -class tilemap038_device : public device_t -{ -public: - typedef device_delegate tmap038_cb_delegate; - - tilemap038_device(const machine_config &mconfig, const char *tag, device_t *owner) - : tilemap038_device(mconfig, tag, owner, (u32)0) - { - } - - tilemap038_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); - - // configurations - template void set_gfxdecode_tag(T &&tag) { m_gfxdecode.set_tag(std::forward(tag)); } - template void set_tile_callback(T &&... args) { m_038_cb.set(std::forward(args)...); } - void set_gfx(u16 no) { m_gfxno = no; } - void set_xoffs(int xoffs, int flipped_xoffs) { m_xoffs = xoffs; m_flipped_xoffs = flipped_xoffs; } - void set_yoffs(int yoffs, int flipped_yoffs) { m_yoffs = yoffs; m_flipped_yoffs = flipped_yoffs; } - - // call to do the rendering etc. - template - void draw_common(screen_device &screen, BitmapClass &bitmap, const rectangle &cliprect, u32 flags, u8 pri = 0, u8 pri_mask = ~0); - - void prepare(); - void draw(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, u32 flags, u8 pri = 0, u8 pri_mask = ~0); - void draw(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect, u32 flags, u8 pri = 0, u8 pri_mask = ~0); - - // access - void vram_map(address_map &map); - void vram_8x8_map(address_map &map); - void vram_16x16_map(address_map &map); - - void vram_writeonly_map(address_map &map); - void vram_16x16_writeonly_map(address_map &map); - - u16 vram_8x8_r(offs_t offset); - void vram_8x8_w(offs_t offset, u16 data, u16 mem_mask); - - u16 vram_16x16_r(offs_t offset); - void vram_16x16_w(offs_t offset, u16 data, u16 mem_mask); - - u16 lineram_r(offs_t offset) { return m_lineram[offset]; } - void lineram_w(offs_t offset, u16 data, u16 mem_mask = ~0) { COMBINE_DATA(&m_lineram[offset]); } - - u16 vregs_r(offs_t offset) { return m_vregs[offset]; } - void vregs_w(offs_t offset, u16 data, u16 mem_mask = ~0) { COMBINE_DATA(&m_vregs[offset]); } - - void mark_all_dirty() { m_tmap->mark_all_dirty(); } - void set_flip(u32 attributes) { m_tmap->set_flip(attributes); } - void set_palette_offset(u32 offset) { m_tmap->set_palette_offset(offset); } - void set_scroll_rows(u32 scroll_rows) { m_tmap->set_scroll_rows(scroll_rows); } - void set_scroll_cols(u32 scroll_cols) { m_tmap->set_scroll_cols(scroll_cols); } - void set_scrollx(int which, int value) { m_tmap->set_scrollx(which, value); } - void set_scrolly(int which, int value) { m_tmap->set_scrolly(which, value); } - - // getters - u16 lineram(offs_t offset) const { return m_lineram[offset]; } - - u16 rowscroll(offs_t line) const { return rowscroll_en() ? m_lineram[((line & 0x1ff) * 2) + 0] : 0; } - u16 rowselect(offs_t line) const { return rowselect_en() ? m_lineram[((line & 0x1ff) * 2) + 1] : 0; } - - u16 vregs(offs_t offset) const { return m_vregs[offset]; } - - // vregs - bool flipx() const { return BIT(~m_vregs[0], 15); } - bool rowscroll_en() const { return BIT(m_vregs[0], 14) && (m_lineram != nullptr); } - int scrollx() const { return (m_vregs[0] & 0x1ff) + (flipx() ? m_flipped_xoffs : m_xoffs); } - - bool flipy() const { return BIT(~m_vregs[1], 15); } - bool rowselect_en() const { return BIT(m_vregs[1], 14) && (m_lineram != nullptr); } - bool tiledim() const { return m_tiledim; } - int scrolly() const { return (m_vregs[1] & 0x1ff) + (flipy() ? m_flipped_yoffs : m_yoffs); } - - bool enable() const { return BIT(~m_vregs[2], 4); } - u16 external() const { return m_vregs[2] & 0xf; } - - bool tile_is_8x8() const { return (!m_tiledim) || (m_vram_16x16 == nullptr); } - bool tile_is_16x16() const { return m_tiledim || (m_vram_8x8 == nullptr); } -protected: - virtual void device_start() override; - virtual void device_reset() override; - -private: - TILE_GET_INFO_MEMBER(get_tile_info); - optional_shared_ptr m_vram_8x8; - optional_shared_ptr m_vram_16x16; - optional_shared_ptr m_lineram; - std::unique_ptr m_vregs; - bool m_tiledim; - - // set when creating device - required_device m_gfxdecode; - u16 m_gfxno; - - tmap038_cb_delegate m_038_cb; - tilemap_t* m_tmap = nullptr; - - int m_xoffs, m_flipped_xoffs; - int m_yoffs, m_flipped_yoffs; -}; - - -DECLARE_DEVICE_TYPE(TMAP038, tilemap038_device) - -#endif // MAME_VIDEO_TMAP038_H diff --git a/src/mame/upl/ninjakd2.cpp b/src/mame/upl/ninjakd2.cpp index 6fbc9b61ae3..4d9284bb8e1 100644 --- a/src/mame/upl/ninjakd2.cpp +++ b/src/mame/upl/ninjakd2.cpp @@ -153,8 +153,7 @@ TODO: #include "emu.h" #include "ninjakd2.h" -#include "mc8123.h" - +#include "cpu/z80/mc8123.h" #include "cpu/z80/z80.h" #include "machine/gen_latch.h" diff --git a/src/mame/vsystem/crshrace.h b/src/mame/vsystem/crshrace.h index 029bab186f7..66088e19707 100644 --- a/src/mame/vsystem/crshrace.h +++ b/src/mame/vsystem/crshrace.h @@ -7,11 +7,10 @@ #include "vsystem_spr.h" -#include "k053936.h" - #include "cpu/z80/z80.h" #include "machine/gen_latch.h" #include "video/bufsprite.h" +#include "video/k053936.h" #include "emupal.h" #include "tilemap.h" diff --git a/src/mame/vsystem/f1gp.h b/src/mame/vsystem/f1gp.h index d1bb58920b8..cccc0410fce 100644 --- a/src/mame/vsystem/f1gp.h +++ b/src/mame/vsystem/f1gp.h @@ -8,10 +8,9 @@ #include "vsystem_spr.h" #include "vsystem_spr2.h" -#include "k053936.h" - #include "machine/6850acia.h" #include "machine/gen_latch.h" +#include "video/k053936.h" #include "emupal.h" #include "tilemap.h" diff --git a/src/mame/vsystem/suprslam.h b/src/mame/vsystem/suprslam.h index 5c353d67581..fb2b205bbce 100644 --- a/src/mame/vsystem/suprslam.h +++ b/src/mame/vsystem/suprslam.h @@ -12,9 +12,8 @@ #include "vsystem_spr.h" -#include "k053936.h" - #include "machine/gen_latch.h" +#include "video/k053936.h" #include "tilemap.h" diff --git a/src/mame/vsystem/tail2nos.cpp b/src/mame/vsystem/tail2nos.cpp index 886eb0ee716..5e4ddb6a50e 100644 --- a/src/mame/vsystem/tail2nos.cpp +++ b/src/mame/vsystem/tail2nos.cpp @@ -18,13 +18,12 @@ #include "vsystem_gga.h" -#include "k051316.h" - #include "cpu/m68000/m68000.h" #include "cpu/z80/z80.h" #include "machine/6850acia.h" #include "machine/gen_latch.h" #include "sound/ymopn.h" +#include "video/k051316.h" #include "emupal.h" #include "screen.h" -- cgit v1.2.3