summaryrefslogblamecommitdiffstatshomepage
path: root/src/devices/machine/roc10937.cpp
blob: c76e02f13e616b0bed6e8d094efc0a0548c2f133 (plain) (tree)
1
2
3
4
5
6
7
8
9

                                  






                                                                       
                

                     

















                                                    
                                                        
                                                               
                                                                        

  
                                      
                                  






















































                                                          
                                         


                                         
                                                 
                                        
                                                 
                                         


                                         

  
 
                                                                           



















                                  
                                                         
 
                                                                                                                                                                                  
                                                                           
 
                     

 
 
                                                          
 


                                                     
 

                             
                                    
                                      



                                       



                                      

                                
                                
                                
 


                       
 
                             
 
                         






                           
                   

                   
 

                                                


                                                                           
                                          
 
                                                                                                                       
 


                                                                           

                                 
                         
 
 
                               
 
                                 
         
                                                       
                                                                                               


         


                                   

 

                                   


                       
                                  
 





                                                                                           
 
 


                                     
         















                                                         
         
                       


                                                                           
                                                                                                     
                                                                                                                              
 
                     

 
                                                       
 
                                                                                                   
                                                                                                          
 
                     
 
 










                                                                   
 









                                                              
                 


                         
                     












                                                                             
 






                                                                 
         

 
                                                         
 
                                                                                                     
                                                                                                                              
 
                     
 
 

                                     


                                                         
                                                      
                                                                   


                                                              
                                     
 

                                                              


                                                              
                                                     


                                                             

                                                         




                             



                                       

                                                             

                                     
                                                             

                                       
                                                             

                                     
                         
                                                           


                                 

                                                                             
 

                                                                 
                         
                                                 


                         

         


                                                       
                                                                                                   



                                                                                                                                   
// license:BSD-3-Clause
// copyright-holders:James Wallace
/**********************************************************************

    Rockwell 10937/10957 interface and emulation by J.Wallace
    OKI MSC1937 is a clone of this chip

**********************************************************************/

#include "emu.h"
#include "roc10937.h"

/*
   Rockwell 10937 16 segment charset lookup table
     0     1
    ---- ----
   |\   |   /|
 7 | \F |8 /9| 2
   |  \ | /  |
    -E-- --A-
   |  / | \  |
 6 | /D |C \B| 3
   |/   |   \|
    ---- ----  .11
      5    4   ,10

In 14 segment mode, 0 represents the whole top line,
and 5 the bottom line, allowing both modes to share
a charset.

Note that, although we call this a '16 segment' display,
we actually have 18 segments, including the semicolon portions.
16-bit tables are used to hold the main characters, the rest are OR'd in
*/

static const UINT16 roc10937charset[]=
{           // FEDC BA98 7654 3210
	0x507F, // 0101 0000 0111 1111 @.
	0x44CF, // 0100 0100 1100 1111 A.
	0x153F, // 0001 0101 0011 1111 B.
	0x00F3, // 0000 0000 1111 0011 C.
	0x113F, // 0001 0001 0011 1111 D.
	0x40F3, // 0100 0000 1111 0011 E.
	0x40C3, // 0100 0000 1100 0011 F.
	0x04FB, // 0000 0100 1111 1011 G.
	0x44CC, // 0100 0100 1100 1100 H.
	0x1133, // 0001 0001 0011 0011 I.
	0x007C, // 0000 0000 0111 1100 J.
	0x4AC0, // 0100 1010 1100 0000 K.
	0x00F0, // 0000 0000 1111 0000 L.
	0x82CC, // 1000 0010 1100 1100 M.
	0x88CC, // 1000 1000 1100 1100 N.
	0x00FF, // 0000 0000 1111 1111 O.
	0x44C7, // 0100 0100 1100 0111 P.
	0x08FF, // 0000 1000 1111 1111 Q.
	0x4CC7, // 0100 1100 1100 0111 R.
	0x44BB, // 0100 0100 1011 1011 S.
	0x1103, // 0001 0001 0000 0011 T.
	0x00FC, // 0000 0000 1111 1100 U.
	0x22C0, // 0010 0010 1100 0000 V.
	0x28CC, // 0010 1000 1100 1100 W.
	0xAA00, // 1010 1010 0000 0000 X.
	0x9200, // 1001 0010 0000 0000 Y.
	0x2233, // 0010 0010 0011 0011 Z.
	0x00E1, // 0000 0000 1110 0001 [.
	0x8800, // 1000 1000 0000 0000 \.
	0x001E, // 0000 0000 0001 1110 ].
	0x2800, // 0010 1000 0000 0000 ^.
	0x0030, // 0000 0000 0011 0000 _.
	0x0000, // 0000 0000 0000 0000 dummy.
	0x8121, // 1000 0001 0010 0001 !.
	0x0180, // 0000 0001 1000 0000 ".
	0x553C, // 0101 0101 0011 1100 #.
	0x55BB, // 0101 0101 1011 1011 $.
	0x7799, // 0111 0111 1001 1001 %.
	0xC979, // 1100 1001 0111 1001 &.
	0x0200, // 0000 0010 0000 0000 '.
	0x0A00, // 0000 1010 0000 0000 (.
	0xA050, // 1010 0000 0000 0000 ).
	0xFF00, // 1111 1111 0000 0000 *.
	0x5500, // 0101 0101 0000 0000 +.
	0x0000, // 0000 0000 0000 0000 ;. (Set separately)
	0x4400, // 0100 0100 0000 0000 --.
	0x0000, // 0000 0000 0000 0000 . .(Set separately)
	0x2200, // 0010 0010 0000 0000 /.
	0x22FF, // 0010 0010 1111 1111 0.
	0x1100, // 0001 0001 0000 0000 1.
	0x4477, // 0100 0100 0111 0111 2.
	0x443F, // 0100 0100 0011 1111 3.
	0x448C, // 0100 0100 1000 1100 4.
	0x44BB, // 0100 0100 1011 1011 5.
	0x44FB, // 0100 0100 1111 1011 6.
	0x000F, // 0000 0000 0000 1111 7.
	0x44FF, // 0100 0100 1111 1111 8.
	0x44BF, // 0100 0100 1011 1111 9.
	0x0021, // 0000 0000 0010 0001 -
			//                     -.
	0x2001, // 0010 0000 0000 0001 -
			//                     /.
	0x2230, // 0010 0010 0011 0000 <.
	0x4430, // 0100 0100 0011 0000 =.
	0x8830, // 1000 1000 0011 0000 >.
	0x1407, // 0001 0100 0000 0111 ?.
};


///////////////////////////////////////////////////////////////////////////
static const int roc10937poslut[]=
{
	1,//0
	2,
	3,
	4,
	5,
	6,
	7,
	8,
	9,
	10,
	11,
	12,
	13,
	14,
	15,
	0//15
};

const device_type ROC10937 = &device_creator<roc10937_t>;

rocvfd_t::rocvfd_t(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, const char *source) :
	device_t(mconfig, type, name, tag, owner, clock, shortname, source)
{
	m_port_val=0;
}


void rocvfd_t::static_set_value(device_t &device, int val)
{
	rocvfd_t &roc = downcast<rocvfd_t &>(device);
	roc.m_port_val = val;
}

void rocvfd_t::device_start()
{
	save_item(NAME(m_port_val));
	save_item(NAME(m_cursor_pos));
	save_item(NAME(m_window_size));
	save_item(NAME(m_shift_count));
	save_item(NAME(m_shift_data));
	save_item(NAME(m_pcursor_pos));
	save_item(NAME(m_chars));
	save_item(NAME(m_outputs));
	save_item(NAME(m_brightness));
	save_item(NAME(m_count));
	save_item(NAME(m_sclk));
	save_item(NAME(m_data));
	save_item(NAME(m_duty));
	save_item(NAME(m_disp));


	device_reset();
}

void rocvfd_t::device_reset()
{
	m_cursor_pos = 0;
	m_window_size = 16;
	m_shift_count = 0;
	m_shift_data = 0;
	m_pcursor_pos = 0;
	m_brightness =31;
	m_count=0;
	m_duty=31;
	m_disp = 0;
	m_sclk = 0;
	m_data = 0;

	memset(m_chars, 0, sizeof(m_chars));
	memset(m_outputs, 0, sizeof(m_outputs));
}

///////////////////////////////////////////////////////////////////////////
UINT32 rocvfd_t::set_display(UINT32 segin)
{
	return BITSWAP32(segin, 31,30,29,28,27,26,25,24,23,22,21,20,19,18,17,16,11,9,15,13,12,8,10,14,7,6,5,4,3,2,1,0);

}

///////////////////////////////////////////////////////////////////////////
void rocvfd_t::device_post_load()
{
	update_display();
}

void rocvfd_t::update_display()
{
	for (int i =0; i<16; i++)
	{
		m_outputs[i] = set_display(m_chars[i]);
		machine().output().set_indexed_value("vfd", (m_port_val*16) + i, m_outputs[i]);
	}
}

WRITE_LINE_MEMBER( rocvfd_t::sclk )
{
	shift_clock(state);
}

WRITE_LINE_MEMBER( rocvfd_t::data )
{
	m_data = state;
}

WRITE_LINE_MEMBER( rocvfd_t::por )
{
	//If line goes low, reset mode is engaged, until such a time as it goes high again.
	if (!state)
	{
		reset();
	}
}


void rocvfd_t::shift_clock(int state)
{
	if (m_sclk != state)
	{
		//Clock data on FALLING edge
		if (!m_sclk)
		{
			m_shift_data <<= 1;

			if ( m_data ) m_shift_data |= 1;

			if ( ++m_shift_count >= 8 )
			{
				write_char(m_shift_data);
				m_shift_count = 0;
				m_shift_data  = 0;
			}
			update_display();

		}
	}
	m_sclk = state;
}

///////////////////////////////////////////////////////////////////////////
roc10937_t::roc10937_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
	: rocvfd_t(mconfig, ROC10937, "Rockwell 10937 VFD controller and compatible", tag, owner, clock, "roc10937", __FILE__)
{
	m_port_val=0;
}

const device_type MSC1937 = &device_creator<msc1937_t>;

msc1937_t::msc1937_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
	: rocvfd_t(mconfig, MSC1937, "OKI MSC1937 VFD controller", tag, owner, clock, "msc1937", __FILE__)
{
	m_port_val=0;
}

void rocvfd_t::write_char(int data)
{
	if ( data & 0x80 )
	{ // Control data received
		if ( (data & 0xF0) == 0xA0 ) // 1010 xxxx
		{ // 1 010 xxxx Buffer Pointer control
			m_cursor_pos = roc10937poslut[data & 0x0F];
		}
		else if ( (data & 0xF0) == 0xC0 ) // 1100 xxxx
		{ // 1100 xxxx Set number of digits
			data &= 0x0F;

			if ( data == 0 ) m_window_size = 16;
			else             m_window_size = data;
		}
		else if ( (data & 0xE0) == 0xE0 ) // 111x xxxx
		{ // 111x xxxx Set duty cycle ( brightness )
			m_brightness = (data & 0x1F);
		}
		else if ( (data & 0xE0) == 0x80 ) // 100x ---
		{ // 100x xxxx Test mode
			m_duty =4;
		}
	}
	else
	{ // Display data
//      data &= 0x3F;

		switch ( data )
		{
			case 0x2C: // ;
			m_chars[m_pcursor_pos] |= (1<<16);//.
			m_chars[m_pcursor_pos] |= (1<<17);//,
			break;
			case 0x2E: //
			m_chars[m_pcursor_pos] |= (1<<16);//.
			break;
			default :
			m_pcursor_pos = m_cursor_pos;
			m_chars[m_cursor_pos] = roc10937charset[data & 0x3F];

			m_cursor_pos++;
			if (  m_cursor_pos > (m_window_size -1) )
			{
				m_cursor_pos = 0;
			}
			break;
		}
	}
}

const device_type ROC10957 = &device_creator<roc10957_t>;

roc10957_t::roc10957_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
	: rocvfd_t(mconfig, ROC10957, "Rockwell 10957 VFD controller and compatible", tag, owner, clock, "roc10957", __FILE__)
{
	m_port_val=0;
}

void roc10957_t::write_char(int data)
{
	if ( data & 0x80 )
	{ // Control data received
		if ( (data & 0xF0) == 0xA0 ) // 1010 xxxx
		{ // 1 010 xxxx Buffer Pointer control
			m_cursor_pos = roc10937poslut[data & 0x0F];
		}
		else if ( (data & 0xF0) == 0xC0 ) // 1100 xxxx
		{ // 1100 xxxx Set number of digits
			data &= 0x0F;

			if ( data == 0 ) m_window_size = 16;
			else             m_window_size = data;
		}
		else if ( (data & 0xE0) == 0xE0 ) // 111x xxxx
		{ // 111x xxxx Set duty cycle ( brightness )
			m_brightness = (data & 0x1F);
		}
		else if ( (data & 0xE0) == 0x80 ) // 100x ---
		{ // 100x xxxx Test mode
			popmessage("TEST MODE ENABLED!");
			m_duty = 4;
		}
	}
	else
	{ // Display data
		data &= 0x3F;

		switch ( data )
		{
			case 0x2C: // ;
			m_chars[m_pcursor_pos] |= (1<<16);//.
			m_chars[m_pcursor_pos] |= (1<<17);//,
			break;
			case 0x2E: //
			m_chars[m_pcursor_pos] |= (1<<16);//.
			break;
			case 0x6C: // ;
			m_chars[m_pcursor_pos] |= (1<<16);//.
			break;
			case 0x6E: //
			{
				m_chars[m_pcursor_pos] = 0;
			}
			break;
			default :
			m_pcursor_pos = m_cursor_pos;
			m_chars[m_cursor_pos] = roc10937charset[data & 0x3F];

			m_cursor_pos++;
			if (  m_cursor_pos > (m_window_size -1) )
			{
				m_cursor_pos = 0;
			}
		break;
		}
	}
}

const device_type S16LF01 = &device_creator<s16lf01_t>;

s16lf01_t::s16lf01_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
	: rocvfd_t(mconfig, S16LF01, "Samsung 16LF01 Series VFD controller and compatible", tag, owner, clock, "s16lf01", __FILE__)
{
	m_port_val=0;
}