224 lines
6.6 KiB
C++
224 lines
6.6 KiB
C++
/**********************************************************************
|
|
|
|
Copyright (C) Antoine Mine' 2008
|
|
|
|
Hewlett Packard HP48 S/SX & G/GX and HP49 G
|
|
|
|
**********************************************************************/
|
|
|
|
#ifdef CHARDEV
|
|
#include "devices/chardev.h"
|
|
#endif
|
|
#include "sound/dac.h"
|
|
/* model */
|
|
typedef enum {
|
|
HP48_S,
|
|
HP48_SX,
|
|
HP48_G,
|
|
HP48_GX,
|
|
HP48_GP,
|
|
HP49_G,
|
|
} hp48_models;
|
|
|
|
/* memory module configuration */
|
|
typedef struct
|
|
{
|
|
/* static part */
|
|
UINT32 off_mask; /* offset bit-mask, indicates the real size */
|
|
read8_delegate read;
|
|
const char *read_name;
|
|
write8_delegate write;
|
|
void* data; /* non-NULL for banks */
|
|
int isnop;
|
|
|
|
/* configurable part */
|
|
UINT8 state; /* one of HP48_MODULE_ */
|
|
UINT32 base; /* base address */
|
|
UINT32 mask; /* often improperly called size, it is an address select mask */
|
|
|
|
} hp48_module;
|
|
|
|
|
|
/* screen image averaging */
|
|
#define HP48_NB_SCREENS 3
|
|
|
|
class hp48_state : public driver_device
|
|
{
|
|
public:
|
|
hp48_state(const machine_config &mconfig, device_type type, const char *tag)
|
|
: driver_device(mconfig, type, tag),
|
|
m_maincpu(*this, "maincpu"),
|
|
m_dac(*this, "dac"),
|
|
m_palette(*this, "palette") { }
|
|
|
|
UINT8 *m_videoram;
|
|
UINT8 m_io[64];
|
|
hp48_models m_model;
|
|
|
|
/* OUT register from SATURN (actually 12-bit) */
|
|
UINT16 m_out;
|
|
|
|
/* keyboard interrupt */
|
|
UINT8 m_kdn;
|
|
|
|
/* from highest to lowest priority: HDW, NCE2, CE1, CE2, NCE3, NCE1 */
|
|
hp48_module m_modules[6];
|
|
|
|
/* RAM/ROM extensions, GX/SX only (each UINT8 stores one nibble)
|
|
port1: SX/GX: 32/128 KB
|
|
port2: SX:32/128KB, GX:128/512/4096 KB
|
|
*/
|
|
UINT32 m_port_size[2];
|
|
UINT8 m_port_write[2];
|
|
UINT8* m_port_data[2];
|
|
|
|
UINT32 m_bank_switch;
|
|
UINT32 m_io_addr;
|
|
UINT16 m_crc;
|
|
UINT8 m_timer1;
|
|
UINT32 m_timer2;
|
|
#ifdef CHARDEV
|
|
chardev* m_chardev;
|
|
#endif
|
|
UINT8 m_screens[ HP48_NB_SCREENS ][ 64 ][ 144 ];
|
|
int m_cur_screen;
|
|
UINT8* m_rom;
|
|
|
|
DECLARE_DRIVER_INIT(hp48);
|
|
virtual void machine_reset();
|
|
DECLARE_PALETTE_INIT(hp48);
|
|
DECLARE_MACHINE_START(hp49g);
|
|
DECLARE_MACHINE_START(hp48gx);
|
|
DECLARE_MACHINE_START(hp48g);
|
|
DECLARE_MACHINE_START(hp48gp);
|
|
DECLARE_MACHINE_START(hp48sx);
|
|
DECLARE_MACHINE_START(hp48s);
|
|
UINT32 screen_update_hp48(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect);
|
|
void hp48_machine_start(hp48_models model);
|
|
DECLARE_WRITE8_MEMBER(hp48_io_w);
|
|
DECLARE_READ8_MEMBER(hp48_io_r);
|
|
DECLARE_READ8_MEMBER(hp48_bank_r);
|
|
DECLARE_WRITE8_MEMBER(hp49_bank_w);
|
|
TIMER_CALLBACK_MEMBER(hp48_rs232_byte_recv_cb);
|
|
TIMER_CALLBACK_MEMBER(hp48_rs232_byte_sent_cb);
|
|
TIMER_CALLBACK_MEMBER(hp48_chardev_byte_recv_cb);
|
|
TIMER_CALLBACK_MEMBER(hp48_kbd_cb);
|
|
TIMER_CALLBACK_MEMBER(hp48_timer1_cb);
|
|
TIMER_CALLBACK_MEMBER(hp48_timer2_cb);
|
|
void hp48_update_annunciators();
|
|
void hp48_apply_modules();
|
|
required_device<cpu_device> m_maincpu;
|
|
required_device<dac_device> m_dac;
|
|
required_device<palette_device> m_palette;
|
|
void hp48_pulse_irq( int irq_line);
|
|
void hp48_rs232_start_recv_byte( UINT8 data );
|
|
void hp48_rs232_send_byte( );
|
|
int hp48_get_in( );
|
|
void hp48_update_kdn( );
|
|
void hp48_reset_modules( );
|
|
void hp48_decode_nibble( UINT8* dst, UINT8* src, int size );
|
|
void hp48_encode_nibble( UINT8* dst, UINT8* src, int size );
|
|
|
|
/* memory controller */
|
|
DECLARE_WRITE_LINE_MEMBER( hp48_mem_reset );
|
|
DECLARE_WRITE32_MEMBER( hp48_mem_config );
|
|
DECLARE_WRITE32_MEMBER( hp48_mem_unconfig );
|
|
DECLARE_READ32_MEMBER( hp48_mem_id );
|
|
|
|
/* CRC computation */
|
|
DECLARE_WRITE32_MEMBER( hp48_mem_crc );
|
|
|
|
/* IN/OUT registers */
|
|
DECLARE_READ32_MEMBER( hp48_reg_in );
|
|
DECLARE_WRITE32_MEMBER( hp48_reg_out );
|
|
|
|
/* keybord interrupt system */
|
|
DECLARE_WRITE_LINE_MEMBER( hp48_rsi );
|
|
};
|
|
|
|
|
|
/***************************************************************************
|
|
MACROS
|
|
***************************************************************************/
|
|
|
|
/* read from I/O memory */
|
|
#define HP48_IO_4(x) (m_io[(x)])
|
|
#define HP48_IO_8(x) (m_io[(x)] | (m_io[(x)+1] << 4))
|
|
#define HP48_IO_12(x) (m_io[(x)] | (m_io[(x)+1] << 4) | (m_io[(x)+2] << 8))
|
|
#define HP48_IO_20(x) (m_io[(x)] | (m_io[(x)+1] << 4) | (m_io[(x)+2] << 8) | \
|
|
(m_io[(x)+3] << 12) | (m_io[(x)+4] << 16))
|
|
|
|
|
|
/*----------- defined in machine/hp48.c -----------*/
|
|
|
|
/***************************************************************************
|
|
GLOBAL VARIABLES & CONSTANTS
|
|
***************************************************************************/
|
|
|
|
/* I/O memory */
|
|
|
|
|
|
|
|
/***************************************************************************
|
|
FUNCTION PROTOTYPES
|
|
***************************************************************************/
|
|
|
|
/* list of memory modules from highest to lowest priority */
|
|
#define HP48_HDW 0
|
|
#define HP48_NCE2 1
|
|
#define HP48_CE1 2
|
|
#define HP48_CE2 3
|
|
#define HP48_NCE3 4
|
|
#define HP48_NCE1 5
|
|
|
|
/****************************** cards ********************************/
|
|
|
|
class hp48_port_image_device : public device_t,
|
|
public device_image_interface
|
|
{
|
|
public:
|
|
// construction/destruction
|
|
hp48_port_image_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
|
|
|
|
static void set_port_config(device_t &device, int port, int module, int max_size)
|
|
{
|
|
downcast<hp48_port_image_device &>(device).m_port = port;
|
|
downcast<hp48_port_image_device &>(device).m_module = module;
|
|
downcast<hp48_port_image_device &>(device).m_max_size = max_size;
|
|
}
|
|
|
|
// image-level overrides
|
|
virtual iodevice_t image_type() const { return IO_MEMCARD; }
|
|
|
|
virtual bool is_readable() const { return 1; }
|
|
virtual bool is_writeable() const { return 1; }
|
|
virtual bool is_creatable() const { return 1; }
|
|
virtual bool must_be_loaded() const { return 0; }
|
|
virtual bool is_reset_on_load() const { return 0; }
|
|
virtual const char *image_interface() const { return NULL; }
|
|
virtual const char *file_extensions() const { return "crd"; }
|
|
virtual const option_guide *create_option_guide() const { return NULL; }
|
|
|
|
virtual bool call_load();
|
|
virtual void call_unload();
|
|
virtual bool call_create(int format_type, option_resolution *format_options);
|
|
protected:
|
|
// device-level overrides
|
|
virtual void device_config_complete();
|
|
virtual void device_start();
|
|
private:
|
|
void hp48_fill_port();
|
|
void hp48_unfill_port();
|
|
|
|
int m_port; /* port index: 0 or 1 (for port 1 and 2) */
|
|
int m_module; /* memory module where the port is visible */
|
|
int m_max_size; /* maximum size, in bytes 128 KB or 4 GB */
|
|
};
|
|
|
|
// device type definition
|
|
extern const device_type HP48_PORT;
|
|
|
|
#define MCFG_HP48_PORT_ADD(_tag, _port, _module, _max_size) \
|
|
MCFG_DEVICE_ADD(_tag, HP48_PORT, 0) \
|
|
hp48_port_image_device::set_port_config(*device, _port, _module, _max_size);
|