From ef22c02ba10435860f3d468f4e4115fbd54e5849 Mon Sep 17 00:00:00 2001 From: Hatsune Mike Date: Thu, 6 Jun 2024 11:31:41 +0900 Subject: [PATCH] sega/segac2.cpp: Addition of Print Club V3; some minor changes for the other Print Club boards; many notes added to the C2 driver near the top (#12402) New NOT WORKING machines ------------------------------ Print Club (Japan Vol.3) [Hatsune Mike] --- src/emu/xtal.cpp | 1 + src/mame/mame.lst | 1 + src/mame/sega/segac2.cpp | 135 +++++++++++++++++++++++++++++++++++++-- 3 files changed, 132 insertions(+), 5 deletions(-) diff --git a/src/emu/xtal.cpp b/src/emu/xtal.cpp index 25733f73dcf..d7ab1e039c5 100644 --- a/src/emu/xtal.cpp +++ b/src/emu/xtal.cpp @@ -475,6 +475,7 @@ const double XTAL::known_xtals[] = { 51'200'000, /* 51.2_MHz_XTAL Namco Super System 22 video clock */ 52'000'000, /* 52_MHz_XTAL Cojag */ 52'832'000, /* 52.832_MHz_XTAL Wang PC TIG video controller */ + 52'867'000, /* 52.867_MHz_XTAL Atlus Print Club (Sega C2 PCB) */ 53'203'424, /* 53.203424_MHz_XTAL Master System, Mega Drive PAL (12x PAL subcarrier) */ 53'693'175, /* 53.693175_MHz_XTAL PSX-based h/w, Sony ZN1-2-based (15x NTSC subcarrier) */ 54'000'000, /* 54_MHz_XTAL Taito JC */ diff --git a/src/mame/mame.lst b/src/mame/mame.lst index deb8f5d6e2f..4b1e5761f63 100644 --- a/src/mame/mame.lst +++ b/src/mame/mame.lst @@ -39760,6 +39760,7 @@ ooparts // (c) 1992 Success pclubj // pclubjv2 // pclub // +pclubjv3 // pclubjv4 // pclubjv5 // potopoto // (c) 1994 Sega diff --git a/src/mame/sega/segac2.cpp b/src/mame/sega/segac2.cpp index eeb36cfd24f..7b6bd312921 100644 --- a/src/mame/sega/segac2.cpp +++ b/src/mame/sega/segac2.cpp @@ -43,6 +43,7 @@ 1995 Print Club (Vol.1) Atlus ? C2 1995 Print Club (Vol.2) Atlus ? C2 + 1996 Print Club (Vol.3) Atlus 317-5030 C2 1996 Print Club (Vol.4) Atlus ? C2 1996 Print Club (Vol.5) Atlus ? C2 @@ -62,6 +63,86 @@ - Correct ROM labels for: ssonicbr, ooparts, headonch - Does ooparts actually use upd samples? PCB has the same rom as tfrceac - Is the joystick hack for ooparts unofficial, or done by Sega for location test? + - Puyo Puyo 2 VS link capabilities + + The "Print Club" boards used by Atlus are variants of the C2 board. Important differences: + - XL2 is 52.867MHz, instead of 53.693MHz. + - The 315-5242 DAC is on a riser board called 837-7694. It has two 74LS273 ICs + between the original DAC location and its spot on the riser. + - There is a daughterboard attached to CN4, which is also populated in the reverse + orientation compared to a normal C2 with CN4 populated (in terms of the polarizing + key orientation). + - The daughterboard is labeled 839-0805, and contains a TC82C55AM IO control IC, + as well as some 74 series glue logic and passives. This board talks to other + devices used in the print club machine. This board has a 1990 stamp on it, which + dates it much earlier than the known Atlus Print Club games. + - There is a larger board responsible for RGB multiplexing and encoding, named + 837-10507-01. It takes RGB in from both the C2 PCB and (presumably) the camera. + ICs of note include Sony V7040, Sony CXA1688M, SBX1744-01 (submodule). + It has two sets of RCA jacks, likely for NTSC-compatible camera input. + - The wiring harness has power connections and monitor connections similar to or + directly compatible with that of a Sega New Astro City monitor and power supply. + + With XL2 replaced, the DAC brought down from the riser, CN4 rotated 180 degrees, and + the I/O daughterboard disconnected, it becomes a normal C2 PCB. + + Notes regarding Puyo Puyo 2's link capabilities (Mike Moffitt 2024-05-24): + + Puyo Puyo 2 boards often (but not always) have CN4 populated. There exists a daughterboard + that can be installed to allow two PCBs to be networked for a four player mode. A video has + been shown that confirms this functionality works, but supposedly this peripheral was not + released by Compile/Sega and thus never reached mass production. A reproduction exists but + is not for sale, and documentation of its functionality does not yet exist. + + From what I can tell, the daughtercard at CN4 is mapped into odd bytes at $880100. I think + it is a small amount of RAM, shared with a Z80 processor or compatible microcontroller. + + Puyo Puyo 2 has a task that runs periodically to assess the status of the versus network. + Its initialization looks like this as far as I can tell at the time of writing: + + CommMessage := $880101 + CommStatus := $88010F + CommCommand := $880111 + CommControl := $880131 + + - Write $01 to CommControl, then write $00 six frames later (reset message?) + - Sleep for 120 frames (two seconds) + - Go back to top if the current frame count is not a multiple of 4... + - Write $FC to CommCommand (signature request) + - Look for a signature string "PUYO2Z80" from CommMessage (on odd bytes) + If the signature has a mismatch, the process begins from the top. + From this point the test menu will show that the comm board status is OK. + - Write $FD to CommCommand (CRC request) + If the result is zero, the test menu will clear the CRC error and proceed. + - Now the string "PUYO268K" is written out to CommMessage (on odd bytes), across + eight frames (one char per frame). Each write looks like this: + * Write $FF to CommCommand + * Write $01 to CommStatus + * Write $FD to CommCommand + * Write the character to CommMessage + (2 * index) + * Increment index, yield for one frame + - Once again check that the current frame count is a multiple of 4, and if not, + abort and go to the top of this process. + - Command $FD is written once more (CRC request?) and we expect to see $FF in all + eight characters of CommMessage + - The test routine marks the board as good, but not yet the loop test. + - Yield for one frame. + - Command $FE is written to CommCommand, and it's expected that CommMessage's first + byte is $00, otherwise the process rests. + - With the $00 response identified, the status has the loop OK bit set, and the link + status is entirely satisfactory. The test menu then proceeds to allow TX/RX. + - The link task accepts a new routine pointer and stores it in its TCB to handle comms. + + This task runs in the background, doing this init periodically if a link isn't established. + The test menu only exposes the current status but doesn't do anything to affect it, aside + from letting the user manually reset the link status. + + The string would imply that there should be a Z80 system on the board, and some shared RAM. + The 68000 side does not write a program of any sort to this IO area, so it's unlikely the + Z80 software is packed into the C2 code anywhere (and I cannot find the PUYO2Z80 string). + + How the TX/RX works is not yet understood. + Thanks: (in no particular order) to any MameDev that helped me out .. (OG, Mish etc.) Charles MacDonald for his C2Emu .. without it working out what were bugs in my code @@ -100,6 +181,8 @@ namespace { #define XL1_CLOCK XTAL(640'000) #define XL2_CLOCK XTAL(53'693'175) +// The Print Club PCBs use a slightly different master clock, likely for genlock compatibility. +#define XL2_CLOCK_PCLUB XTAL(52'867'000) typedef device_delegate segac2_prot_delegate; @@ -250,11 +333,14 @@ public: : segac2_state(mconfig, type, tag) { } + void pclub(machine_config &config); + static constexpr feature_type unemulated_features() { return feature::CAMERA | feature::PRINTER; } void init_pclub(); void init_pclubj(); void init_pclubjv2(); + void init_pclubjv3(); void init_pclubjv4(); void init_pclubjv5(); @@ -266,6 +352,7 @@ private: int prot_func_pclub(int in); int prot_func_pclubjv2(int in); + int prot_func_pclubjv3(int in); int prot_func_pclubjv4(int in); int prot_func_pclubjv5(int in); }; @@ -1850,6 +1937,13 @@ void segac2_state::ribbit(machine_config& config) m_upd7759->set_start_delay(250); } +void pclub_state::pclub(machine_config& config) +{ + segac2(config); + // Print Club boards use a different crystal, possibly for better compatibility with the camera timings. + m_maincpu->set_clock(XL2_CLOCK_PCLUB/6); +} + /****************************************************************************** Rom Definitions @@ -2434,6 +2528,18 @@ ROM_START( pclubjv2 ) /* Print Club vol.2 (c)1995 Atlus */ ROM_END +ROM_START( pclubjv3 ) /* Print Club vol.3 (c)1996 Atlus */ + ROM_REGION( 0x200000, "maincpu", 0 ) + ROM_LOAD16_BYTE( "ic32-p3jsp.ic32", 0x000000, 0x080000, CRC(cb5b6221) SHA1(43c1352bfcaa4012019ae58742a5d09c3c4e5a8f) ) + ROM_LOAD16_BYTE( "ic31-p3jsp.ic31", 0x000001, 0x080000, CRC(cdec8418) SHA1(7b5d6316182ec89230984b617ce0404ea0f1c331) ) + ROM_LOAD16_BYTE( "ic34-p3jsp.ic34", 0x100000, 0x080000, CRC(c33f71a3) SHA1(21f9de9db4504307d5290c11dc86bfed9ee23ef0) ) + ROM_LOAD16_BYTE( "ic33-p3jsp.ic33", 0x100001, 0x080000, CRC(c8da13e4) SHA1(38434f628b43549a234cf612f8a22993c76c20f0) ) + + ROM_REGION( 0x080000, "upd", 0 ) + ROM_LOAD( "epr18169.4", 0x000000, 0x080000, CRC(5c00ccfb) SHA1(d043ffa6528bb9b76774c96df4edf8222a1878a4) ) +ROM_END + + ROM_START( pclubjv4 ) /* Print Club vol.4 (c)1996 Atlus */ ROM_REGION( 0x200000, "maincpu", 0 ) ROM_LOAD16_BYTE( "p4jsm.u32", 0x000000, 0x080000, CRC(36ff5f80) SHA1(33872aa00c8ca3f54dd7503a44562fbdad92df7d) ) @@ -2702,6 +2808,17 @@ int pclub_state::prot_func_pclubjv2(int in) return (b3 << 3) | (b2 << 2) | (b1 << 1) | b0; } +int pclub_state::prot_func_pclubjv3(int in) +{ + // TODO: Determine correctly. This is just copied from V2 as a placeholder. + int const b0 = (BIT( in,3) && BIT(~in,4)) ^ ((BIT(~in,1) && BIT(~in,7)) || BIT( in,6)); + int const b1 = (BIT( in,0) && BIT( in,5)) ^ (BIT( in,2) && BIT(~in,6)); + int const b2 = (BIT(~in,1) && BIT( in,6)) ^ (BIT( in,3) || BIT(~in,5) || BIT(~in,1)); // 1 repeated + int const b3 = (BIT(~in,2) && BIT(~in,7)) ^ (BIT(~in,0) || BIT(~in,4)); + + return (b3 << 3) | (b2 << 2) | (b1 << 1) | b0; +} + int pclub_state::prot_func_pclubjv4(int in) { int const b0 = (BIT(~in,2) && BIT( in,4)) ^ (BIT( in,1) && BIT(~in,6) && BIT(~in,3)); @@ -2852,6 +2969,12 @@ void pclub_state::init_pclubjv2() init_pclub(); } +void pclub_state::init_pclubjv3() +{ + set_prot_func(segac2_prot_delegate(*this, FUNC(pclub_state::prot_func_pclubjv3))); + init_pclub(); +} + void pclub_state::init_pclubjv4() { set_prot_func(segac2_prot_delegate(*this, FUNC(pclub_state::prot_func_pclubjv4))); @@ -2957,11 +3080,13 @@ GAME( 1994, zunkyou, 0, segac2, zunkyou, segac2_state, init_zu GAME( 1994, headonch, 0, segac2, headonch, segac2_state, init_noprot, ROT0, "hack", "Monita to Rimoko no Head On Channel (prototype, hack)", 0 ) /* Atlus Print Club 'Games' (C-2 Hardware) requires printer and camera emulation */ -GAME( 1995, pclubj, 0, segac2, pclub, pclub_state, init_pclubj, ROT0, "Atlus", "Print Club (Japan Vol.1)", MACHINE_NOT_WORKING ) +GAME( 1995, pclubj, 0, pclub, pclub, pclub_state, init_pclubj, ROT0, "Atlus", "Print Club (Japan Vol.1)", MACHINE_NOT_WORKING ) -GAME( 1995, pclubjv2, 0, segac2, pclubjv2, pclub_state, init_pclubjv2, ROT0, "Atlus", "Print Club (Japan Vol.2)", MACHINE_NOT_WORKING ) -GAME( 1995, pclub, pclubjv2, segac2, pclubjv2, pclub_state, init_pclubj, ROT0, "Atlus", "Print Club (World)", MACHINE_NOT_WORKING ) // based on Japan Vol.2 but no Vol.2 subtitle +GAME( 1995, pclubjv2, 0, pclub, pclubjv2, pclub_state, init_pclubjv2, ROT0, "Atlus", "Print Club (Japan Vol.2)", MACHINE_NOT_WORKING ) +GAME( 1995, pclub, pclubjv2, pclub, pclubjv2, pclub_state, init_pclubj, ROT0, "Atlus", "Print Club (World)", MACHINE_NOT_WORKING ) // based on Japan Vol.2 but no Vol.2 subtitle -GAME( 1996, pclubjv4, 0, segac2, pclubjv2, pclub_state, init_pclubjv4, ROT0, "Atlus", "Print Club (Japan Vol.4)", MACHINE_NOT_WORKING ) +GAME( 1995, pclubjv3, 0, pclub, pclubjv2, pclub_state, init_pclubjv3, ROT0, "Atlus", "Print Club (Japan Vol.3)", MACHINE_NOT_WORKING ) -GAME( 1996, pclubjv5, 0, segac2, pclubjv2, pclub_state, init_pclubjv5, ROT0, "Atlus", "Print Club (Japan Vol.5)", MACHINE_NOT_WORKING ) +GAME( 1996, pclubjv4, 0, pclub, pclubjv2, pclub_state, init_pclubjv4, ROT0, "Atlus", "Print Club (Japan Vol.4)", MACHINE_NOT_WORKING ) + +GAME( 1996, pclubjv5, 0, pclub, pclubjv2, pclub_state, init_pclubjv5, ROT0, "Atlus", "Print Club (Japan Vol.5)", MACHINE_NOT_WORKING )