summaryrefslogblamecommitdiffstatshomepage
path: root/src/mess/machine/megacdcd.h
blob: 12c3a7d4993b404bf0bf75e484caafda8087a0ea (plain) (tree)
1
2
3
4
5
6
7
8




                            
                                                                                   
 
                                                        

























































                              
                              










                              
                              
                            
                               
                       
                                
                      
                               
                     
                               
                      
                                






                               
                                                    



                                                                                               
         



                                                                                               
         



                                                                                                 
         


                               
                                                                      
 


                              


                                                           
                                                                                                                                      
                                    
                                                         
                                                             
                                                                                                                                                   
                                                             
                                                                                                                                                   
                                                             
                                                                                                                                                   









                                   

                                                                    






                                                                                                           



                                                    
                                                                                                        
                                                                                                 
 




                                                                                                         









                                                                  
                                







                                       







                                

                        
 
                                                       
 


                         



                          

                         
 
                           
 




                                              

                                                 


                                                         







                                                
                                    




















                                                                 
                                                  





                                            


















                                                                     








                                   
                              


                                  
                               
 
 
 
 
                                                        
                                  
                                                    
                                 
 


                                        
 
 













                                                                            
#include "sound/cdda.h"
#include "imagedev/chd_cd.h"


typedef device_delegate<void (int&, UINT8*, UINT16&, UINT16&)> segacd_dma_delegate;

typedef device_delegate<void (void)> interrupt_delegate;


#define READ_MAIN (0x0200)
#define READ_SUB  (0x0300)

#define REG_W_SBOUT  (0x0)
#define REG_W_IFCTRL (0x1)
#define REG_W_DBCL   (0x2)
#define REG_W_DBCH   (0x3)
#define REG_W_DACL   (0x4)
#define REG_W_DACH   (0x5)
#define REG_W_DTTRG  (0x6)
#define REG_W_DTACK  (0x7)
#define REG_W_WAL    (0x8)
#define REG_W_WAH    (0x9)
#define REG_W_CTRL0  (0xA)
#define REG_W_CTRL1  (0xB)
#define REG_W_PTL    (0xC)
#define REG_W_PTH    (0xD)
#define REG_W_CTRL2  (0xE)
#define REG_W_RESET  (0xF)

#define REG_R_COMIN  (0x0)
#define REG_R_IFSTAT (0x1)
#define REG_R_DBCL   (0x2)
#define REG_R_DBCH   (0x3)
#define REG_R_HEAD0  (0x4)
#define REG_R_HEAD1  (0x5)
#define REG_R_HEAD2  (0x6)
#define REG_R_HEAD3  (0x7)
#define REG_R_PTL    (0x8)
#define REG_R_PTH    (0x9)
#define REG_R_WAL    (0xa)
#define REG_R_WAH    (0xb)
#define REG_R_STAT0  (0xc)
#define REG_R_STAT1  (0xd)
#define REG_R_STAT2  (0xe)
#define REG_R_STAT3  (0xf)

#define CMD_STATUS   (0x0)
#define CMD_STOPALL  (0x1)
#define CMD_GETTOC   (0x2)
#define CMD_READ     (0x3)
#define CMD_SEEK     (0x4)
//                   (0x5)
#define CMD_STOP     (0x6)
#define CMD_RESUME   (0x7)
#define CMD_FF       (0x8)
#define CMD_RW       (0x9)
#define CMD_INIT     (0xa)
//                   (0xb)
#define CMD_CLOSE    (0xc)
#define CMD_OPEN     (0xd)
//                   (0xe)
//                   (0xf)


#define TOCCMD_CURPOS    (0x0)
#define TOCCMD_TRKPOS    (0x1)
#define TOCCMD_CURTRK    (0x2)
#define TOCCMD_LENGTH    (0x3)
#define TOCCMD_FIRSTLAST (0x4)
#define TOCCMD_TRACKADDR (0x5)




#define SECTOR_SIZE (2352)

#define SET_CDD_DATA_MODE \
	CDD_CONTROL |= 0x0100;
#define SET_CDD_AUDIO_MODE \
	CDD_CONTROL &= ~0x0100;
#define STOP_CDC_READ \
	SCD_STATUS_CDC &= ~0x01;
#define SET_CDC_READ \
	SCD_STATUS_CDC |= 0x01;
#define SET_CDC_DMA \
	SCD_STATUS_CDC |= 0x08;
#define STOP_CDC_DMA \
	SCD_STATUS_CDC &= ~0x08;
#define SCD_READ_ENABLED \
	(SCD_STATUS_CDC & 1)

#define SCD_DMA_ENABLED \
	(SCD_STATUS_CDC & 0x08)

#define CLEAR_CDD_RESULT \
	CDD_MIN = CDD_SEC = CDD_FRAME = CDD_EXT = 0;
#define CHECK_SCD_LV5_INTERRUPT \
	if (segacd_irq_mask & 0x20) \
	{ \
		machine.device(":segacd:segacd_68k")->execute().set_input_line(5, HOLD_LINE); \
	}
#define CHECK_SCD_LV4_INTERRUPT \
	if (segacd_irq_mask & 0x10) \
	{ \
		machine.device(":segacd:segacd_68k")->execute().set_input_line(4, HOLD_LINE); \
	}
#define CHECK_SCD_LV4_INTERRUPT_A \
	if (segacd_irq_mask & 0x10) \
	{ \
		machine().device(":segacd:segacd_68k")->execute().set_input_line(4, HOLD_LINE); \
	}


#define CURRENT_TRACK_IS_DATA \
	(segacd.toc->tracks[SCD_CURTRK - 1].trktype != CD_TRACK_AUDIO)

#define CDD_PLAYINGCDDA 0x0100
#define CDD_READY       0x0400
#define CDD_STOPPED     0x0900


#define MCFG_SEGACD_HACK_SET_CDC_DO_DMA( _class, _method) \
	lc89510_temp_device::set_CDC_Do_DMA(*device, segacd_dma_delegate(&_class::_method, #_class "::" #_method, NULL, (_class *)0));
#define MCFG_SEGACD_HACK_SET_NEOCD \
	lc89510_temp_device::set_is_neoCD(*device, true);
#define MCFG_SET_TYPE1_INTERRUPT_CALLBACK( _class, _method) \
	lc89510_temp_device::set_type1_interrupt_callback(*device, interrupt_delegate(&_class::_method, #_class "::" #_method, NULL, (_class *)0));
#define MCFG_SET_TYPE2_INTERRUPT_CALLBACK( _class, _method) \
	lc89510_temp_device::set_type2_interrupt_callback(*device, interrupt_delegate(&_class::_method, #_class "::" #_method, NULL, (_class *)0));
#define MCFG_SET_TYPE3_INTERRUPT_CALLBACK( _class, _method) \
	lc89510_temp_device::set_type3_interrupt_callback(*device, interrupt_delegate(&_class::_method, #_class "::" #_method, NULL, (_class *)0));
/* neocd */

#define CD_FRAMES_MINUTE (60 * 75)
#define CD_FRAMES_SECOND (     75)
#define CD_FRAMES_PREGAP ( 2 * 75)

#define SEK_IRQSTATUS_NONE (0x0000)
#define SEK_IRQSTATUS_AUTO (0x2000)
#define SEK_IRQSTATUS_ACK  (0x1000)

#define LC89510_EXTERNAL_BUFFER_SIZE ((32 * 1024 * 2) + SECTOR_SIZE)

class lc89510_temp_device : public device_t
{
public:
	lc89510_temp_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);

	// HACK for DMA handling
	segacd_dma_delegate segacd_dma_callback;
	interrupt_delegate type1_interrupt_callback;
	interrupt_delegate type2_interrupt_callback;
	interrupt_delegate type3_interrupt_callback;

	void Fake_CDC_Do_DMA(int &dmacount, UINT8 *CDC_BUFFER, UINT16 &dma_addrc, UINT16 &destination );
	static void set_CDC_Do_DMA(device_t &device,segacd_dma_delegate new_segacd_dma_callback);

	void dummy_interrupt_callback(void);
	static void set_type1_interrupt_callback(device_t &device,interrupt_delegate interrupt_callback);
	static void set_type2_interrupt_callback(device_t &device,interrupt_delegate interrupt_callback);
	static void set_type3_interrupt_callback(device_t &device,interrupt_delegate interrupt_callback);


	static void set_is_neoCD(device_t &device, bool is_neoCD);


	// HACK for neoCD handling
	bool is_neoCD;


	struct segacd_t
	{
		cdrom_file  *cd;
		const cdrom_toc   *toc;
		UINT32 current_frame;
	};


	segacd_t segacd;

	UINT8    SCD_BUFFER[2560];

	UINT32   SCD_STATUS;
	UINT32   SCD_STATUS_CDC;
	INT32    SCD_CURLBA;
	UINT8    SCD_CURTRK;


	UINT16 CDC_DECODE;
	UINT16 CDC_REG0;
	UINT16 CDC_REG1;

	UINT8 CDC_BUFFER[LC89510_EXTERNAL_BUFFER_SIZE];


	UINT8 CDD_RX[10];
	UINT8 CDD_TX[10];

	UINT32 CDD_STATUS;
	UINT32 CDD_MIN;
	UINT32 CDD_SEC;
	UINT32 CDD_FRAME;
	UINT32 CDD_EXT;

	UINT16 CDD_CONTROL;

	INT16  CDD_DONE;

	inline int to_bcd(int val, bool byte);
	void set_data_audio_mode(void);
	void CDD_DoChecksum(void);
	bool CDD_Check_TX_Checksum(void);
	void CDD_Export(bool neocd_hack = false);
	void scd_ctrl_checks(running_machine& machine);
	void scd_advance_current_readpos(void);
	int Read_LBA_To_Buffer(running_machine& machine);
	void CDD_GetStatus(void);
	void CDD_Stop(running_machine &machine);
	void CDD_GetPos(void);
	void CDD_GetTrackPos(void);
	void CDD_GetTrack(void);
	void CDD_Length(void);
	void CDD_FirstLast(void);
	void CDD_GetTrackAdr(void);
	void CDD_GetTrackType(void);
	UINT32 getmsf_from_regs(void);
	void CDD_Play(running_machine &machine);
	void CDD_Seek(void);
	void CDD_Pause(running_machine &machine);
	void CDD_Resume(running_machine &machine);
	void CDD_FF(running_machine &machine);
	void CDD_RW(running_machine &machine);
	void CDD_Open(void);
	void CDD_Close(void);
	void CDD_Init(void);
	void CDD_Default(void);
	void CDD_Reset(void);
	void CDC_Reset(void);
	void lc89510_Reset(void);
	void CDC_End_Transfer(running_machine& machine);
	void CDC_Do_DMA(running_machine& machine, int rate);
	UINT16 CDC_Host_r(running_machine& machine, UINT16 type);
	UINT8 CDC_Reg_r(void);
	void CDC_Reg_w(UINT8 data);
	void CDD_Process(running_machine& machine, int reason);
	void CDD_Handle_TOC_Commands(void);
	bool CDD_Import(running_machine& machine);
	READ16_MEMBER( segacd_irq_mask_r );
	WRITE16_MEMBER( segacd_irq_mask_w );
	READ16_MEMBER( segacd_cdd_ctrl_r );
	WRITE16_MEMBER( segacd_cdd_ctrl_w );
	READ8_MEMBER( segacd_cdd_rx_r );
	WRITE8_MEMBER( segacd_cdd_tx_w );
	READ16_MEMBER( segacd_cdfader_r );
	WRITE16_MEMBER( segacd_cdfader_w );

	void reset_cd(void);

	WRITE16_MEMBER( segacd_cdc_mode_address_w );
	READ16_MEMBER( segacd_cdc_mode_address_r );
	WRITE16_MEMBER( segacd_cdc_data_w );
	READ16_MEMBER( segacd_cdc_data_r );
	READ16_MEMBER( cdc_data_sub_r );
	READ16_MEMBER( cdc_data_main_r );

	TIMER_DEVICE_CALLBACK_MEMBER( segacd_access_timer_callback );

	UINT16 get_segacd_irq_mask(void) { return segacd_irq_mask; }
	UINT16 segacd_irq_mask;
	cdda_device* m_cdda;

	/* NeoCD */
	UINT16 nff0002;
	UINT16 nff0016;


	INT32 LC8951RegistersR[16];
	INT32 LC8951RegistersW[16];



	bool bNeoCDCommsClock;

	INT32 NeoCDCommsWordCount;

	INT32 NeoCD_StatusHack;




	void NeoCDCommsControl(UINT8 clock, UINT8 send);
	void LC8951UpdateHeader();
	char* LC8915InitTransfer(int NeoCDDMACount);
	void LC8915EndTransfer();

	void neocd_cdd_tx_w(UINT8 data);
	UINT8 neocd_cdd_rx_r();
	void NeoCDCommsReset();


	UINT16 nff0016_r(void);
	void nff0016_set(UINT16 wordValue);
	void nff0002_set(UINT16 wordValue);

protected:
	virtual void device_start();
	virtual void device_reset();
	virtual machine_config_constructor device_mconfig_additions() const;
private:


};

extern const device_type LC89510_TEMP;