Merge pull request #1309 from Risugami/master

Added motion controller to Midway V-Unit
This commit is contained in:
R. Belmont 2016-08-26 08:11:58 -04:00 committed by GitHub
commit 94d69c9c9b
2 changed files with 66 additions and 14 deletions

View File

@ -35,6 +35,7 @@ Known to exist but not dumped:
#include "machine/nvram.h"
#include "includes/midvunit.h"
#include "crusnusa.lh"
#include <iostream>
#define CPU_CLOCK 50000000
@ -56,6 +57,7 @@ void midvunit_state::machine_start()
save_item(NAME(m_shifter_state));
save_item(NAME(m_timer_rate));
save_item(NAME(m_output_mode));
save_item(NAME(m_output));
}
@ -374,10 +376,13 @@ WRITE32_MEMBER(midvunit_state::offroadc_serial_data_w)
READ32_MEMBER(midvunit_state::midvunit_output_r)
{
//need 0x8000 to allow reading of the following:
//0x4700, 0x5100, 0x5300, 0x5600, 0x5700, 0x5800, 0x5900, 0x5A00 (ascii maybe?)
//will softlock the game if it remains 0x8000 as that is not one of the expected branches
return 0;
return m_output;
}
void midvunit_state::set_input(const char *s) {
m_galil_input = s;
m_galil_input_index = 0;
m_galil_input_length = strlen(s);
}
WRITE32_MEMBER(midvunit_state::midvunit_output_w)
@ -389,21 +394,55 @@ WRITE32_MEMBER(midvunit_state::midvunit_output_w)
case 0xF7: m_output_mode = arg; break;
case 0xFB:
switch (m_output_mode) {
case 0x00: break; //device init? 3C 1C are the only 2 writes at boot.
case 0x00:
set_input(":");
m_galil_output_index = 0;
memset(m_galil_output, 0, 450);
break; //device init? 3C 1C are the only 2 writes at boot.
case 0x04: output().set_value("wheel", (arg&0x80)?(0x7F-(arg&0x7F)):(arg|0x80)); break; //wheel motor delta. left < 128 < right. 128 is no change.
case 0x05: for (bit = 0; bit < 8; bit++) output().set_lamp_value(bit, (arg >> bit) & 0x1); break;
case 0x08: break; //called when motion controller reads a 0x8000 from midvunit_output_r and wants a response.
case 0x08: m_output = m_galil_input[m_galil_input_index++] << 8; break; //get next character from input string.
case 0x09:
if (arg != 0xD)
m_galil_cmd += (char)arg;
if (arg != 0xD) {
m_galil_output[m_galil_output_index] = (char)arg;
if (m_galil_output_index < 450)
m_galil_output_index++;
}
else {
osd_printf_error("Galil: %s\n", m_galil_cmd.c_str());
m_galil_cmd.clear();
// G, W, S, and Q are commented out because they are error commands.
// When the motion tests succeeds it will send the program over to
// the motion controller and as this is not a real system it will
// assume it wants to execute them which turns off the motion system.
// If anyone wishes to implement a real Galil motion controller feel
// free to do so. This will only dump everything to stdout.
if (strstr(m_galil_output,"MG \"V\" IBO {$2.0}"))
set_input("V$00");
else if (strstr(m_galil_output,"MG \"X\", _TSX {$2.0}"))
set_input("X$00");
else if (strstr(m_galil_output,"MG \"Y\", _TSY {$2.0}"))
set_input("Y$00");
else if (strstr(m_galil_output,"MG \"Z\", _TSZ {$2.0}"))
set_input("Z$00");
/*else if (strstr(m_galil_output,"MG \"G\""))
set_input("G");
else if (strstr(m_galil_output,"MG \"W\""))
set_input("W");
else if (strstr(m_galil_output,"MG \"S\""))
set_input("S");
else if (strstr(m_galil_output,"MG \"Q\""))
set_input("Q");*/
else
set_input(":");
std::cout << m_galil_output << std::endl;
//osd_printf_error("Galil << %s\n", m_galil_output);
memset(m_galil_output, 0, m_galil_output_index);
m_galil_output_index = 0;
}
break; //Galil command input. ascii inputs terminated with carriage return.
case 0x0A: break; //write 0 to request response. wants to read 0x8000 after?
case 0x0A: m_output = (m_galil_input_index < m_galil_input_length) ? 0x8000 : 0x0; break; //set output to 0x8000 if there is data available, otherwise 0.
case 0x0B: break; //0 written at boot.
case 0x0C: break; //0 written at boot.
case 0x0E: break; //0 written after test.
}
break;
//receives same data as midvunit_sound_w. unsure what its purpose is, but it is redundant.
@ -593,8 +632,15 @@ static INPUT_PORTS_START( crusnusa )
PORT_BIT( 0x0010, IP_ACTIVE_LOW, IPT_BUTTON8 ) PORT_NAME("View 1") /* view 1 */
PORT_BIT( 0x0020, IP_ACTIVE_LOW, IPT_BUTTON9 ) PORT_NAME("View 2") /* view 2 */
PORT_BIT( 0x0040, IP_ACTIVE_LOW, IPT_BUTTON10 ) PORT_NAME("View 3") /* view 3 */
PORT_BIT( 0x0080, IP_ACTIVE_LOW, IPT_BUTTON11 ) PORT_NAME("View 4") /* view 4 */
PORT_BIT( 0xff00, IP_ACTIVE_LOW, IPT_UNUSED )
PORT_BIT( 0x0080, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Motion Stop")
PORT_BIT( 0x0100, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Right Mat")
PORT_BIT( 0x0200, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Rear Mat")
PORT_BIT( 0x0400, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Left Mat")
PORT_BIT( 0x0800, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Front Mat")
PORT_BIT( 0x1000, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Mat Plugin")
PORT_BIT( 0x2000, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Mat Step")
PORT_BIT( 0x4000, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Opto Detector")
PORT_BIT( 0x8000, IP_ACTIVE_HIGH, IPT_SPECIAL ) PORT_NAME("Failsafe Switch")
PORT_START("DSW")
/* DSW2 at U97 */

View File

@ -96,8 +96,13 @@ public:
UINT8 m_video_changed;
emu_timer *m_scanline_timer;
std::unique_ptr<midvunit_renderer> m_poly;
UINT8 m_galil_input_index;
UINT8 m_galil_input_length;
const char *m_galil_input;
UINT8 m_galil_output_index;
char m_galil_output[450];
UINT32 m_output;
UINT8 m_output_mode;
std::string m_galil_cmd;
DECLARE_WRITE32_MEMBER(midvunit_dma_queue_w);
DECLARE_READ32_MEMBER(midvunit_dma_queue_entries_r);
DECLARE_READ32_MEMBER(midvunit_dma_trigger_r);
@ -141,6 +146,7 @@ public:
DECLARE_DRIVER_INIT(wargods);
DECLARE_DRIVER_INIT(offroadc);
DECLARE_DRIVER_INIT(crusnusa);
void set_input(const char *s);
void init_crusnwld_common(offs_t speedup);
void init_crusnusa_common(offs_t speedup);
virtual void machine_start() override;