#include "HT45F24A.h"
/********************************************************/
/*****************Requires the user to set**************/
#define tmro_value 90;			      //tmro_value=SystemFrequency/(4*SAMPLINGRATE)			
#define amplifier_ce		_pcc0	  //the HT82V739 CE  control pin 
#define amplifier_ce_c		_pc0
#define flash_vss_c			_pcc1	  //the Flash Vss control pin
#define flash_vss			_pc1
/***************** Voice registers*********************/
unsigned  char controlcode;
unsigned  char voice_data_l,voice_data_h;
unsigned  char voice_length_h,voice_length_L;
/******************************************************/
typedef unsigned char __FG1_byte;
typedef struct {
volatile unsigned char b0:1;
volatile unsigned char b1:1;
volatile unsigned char b2:1;
volatile unsigned char b3:1;
volatile unsigned char b4:1;
volatile unsigned char b5:1;
volatile unsigned char b6:1;
volatile unsigned char b7:1;
} __fg1_bits;
typedef union {
__fg1_bits bits;
__FG1_byte byte;
} __byte_type;
__byte_type bitvar;
/********************************************************/
/****************** Voice Flag *************************/
#define Fg_FirstPCM12Data 	 bitvar.bits.b0
#define Fg_Voice_END	 	 bitvar.bits.b1

/********************************************************/
//********************Function void*********************/
void  _send_voice_byte(unsigned char send_data);
void PLAY_VOICE(unsigned char voice_num);
void _VOICEDOWN(void);
void _VOICEUP(void);
void  _Get_Send_Byte(void); 

/******************************PLAY_VOICE****************************/		
void PLAY_VOICE(unsigned char voice_num)
{
volatile unsigned char 	voice_address_index_l;
volatile unsigned char 	voice_address_index_m;
volatile unsigned char 	voice_address_index_h;
	
volatile unsigned char 	voice_start_address_h;
volatile unsigned char 	voice_start_address_m;
volatile unsigned char 	voice_start_address_l;

//Enable the HT82V739 and Flash
	amplifier_ce_c	=0x00;				
	amplifier_ce	=0x00;
	flash_vss_c		=0x00;
	flash_vss		=0x00;
	_VOICEUP();
//Get Voice address index
	voice_address_index_l=voice_num<<0x02;
	voice_address_index_l=voice_address_index_l-voice_num+0x20;
	voice_address_index_m=0x00;
	voice_address_index_h=0x00;
//	init SPI/FALSH
	_simc0=0x02;		
	_simc2=0x3c;	
	_emi=0x00;
//SPI HighSpeed Read get the voice start address
	_csen=0x01;
	_send_voice_byte(0x0b);	
	_send_voice_byte(voice_address_index_h);
	_send_voice_byte(voice_address_index_m);
	_send_voice_byte(voice_address_index_l);
	_send_voice_byte(0x00);

	GCC_CLRWDT();
	_Get_Send_Byte();
	voice_start_address_l=_acc;	
	
	_Get_Send_Byte();
	voice_start_address_m=_acc;	
	
	_Get_Send_Byte();
	voice_start_address_h=_acc;	

	_csen=0;
//get the voice data  start address	
	GCC_CLRWDT(); 
	voice_start_address_l=voice_start_address_l+0x09;
	
//SPI HighSpeed Read	
	_csen=1;

	_send_voice_byte(0x0b);	
	_send_voice_byte(voice_start_address_h);
	_send_voice_byte(voice_start_address_m);	
	_send_voice_byte(voice_start_address_l);
	_send_voice_byte(0x00);

	GCC_CLRWDT();
//init the timer ,DAC and voice ram
	_tmr0c=0x82;
	_tmr0=0xff-tmro_value;
	
	_emi=1;
	_et0i=1;
	_t0on=1;
	
	voice_length_L=0x00;
	voice_length_h=0x00;
	Fg_Voice_END=0x00;	
	controlcode=0x55;
	
	_dactrl=0x61;
	
	while(!Fg_Voice_END)
	GCC_CLRWDT();
//	Finish play voice 
	_t0on=0x00;
	_emi=0x00;
	flash_vss_c=0x00;
	flash_vss=0x01;
	_VOICEDOWN();
	amplifier_ce_c=0x00;
	amplifier_ce=0x01;
	_dactrl=0xE0;
	_csen=0x00;
	_simen=0x00;	
}
   
/**************************_Get_Send_Byte*******************************/
void  _send_voice_byte(unsigned char send_data)   
{	         
	_wcol=0;
	_trf=0;
	_simd=_acc;
	while (_wcol);
	while (!_trf);
	_acc=_simd;
}

/***************************_VOICEUP**********************************/
void _VOICEUP(void)
{
          _dah=0;                         
          _dal=0;  
          voice_data_l=0; 
          voice_data_h=0; 
voiceup:                                
        GCC_CLRWDT();
        
        _acc=4;
        while (_acc>0)
        {
        _acc=_acc-1;
        }   
         _acc=voice_data_h&0b10000000;

        if (0b10000000!=_acc)
          {	
          	voice_data_l=voice_data_l+0x10;
          	if(_c=1)
          		voice_data_h=voice_data_h+1;
          		_dal=voice_data_l;
          		_dah=voice_data_h;	
          		goto     voiceup;    
          }         
}
/**************************_VOICEDOWN*******************************/
void _VOICEDOWN(void)
{
 		 _dal=voice_data_l;
         _dah=voice_data_h;  
voicedwn:                               
        GCC_CLRWDT(); 
        _acc=4;
        while (_acc>0)
        {
        _acc=_acc-1;
        }  

		if((_dal!=0x00)|(_dah!=0x00))	
		{
				if(_dal==0x00)
				{
					_dah=_dah-1;
					_dal=0xf0;					
				}
				else										
				_dal=_dal-0x10;
        goto     voicedwn; 
		}
		else
	    GCC_CLRWDT(); 

}
	

/******************Get_Voice_Data_ISR /timer interrupt*****************/
void __attribute((interrupt(0x0C))) Get_Voice_Data_ISR(void)
{//Getting Voice data into the DAC
	switch (controlcode)
	{	
	case 0x06:
	case 0x00:
		_dal=voice_data_l;
		_dah=voice_data_h;		
		if((voice_length_L==0x00)&(voice_length_h==0x00))
			{ 
				controlcode=0x55;
				break;
			}
		else	
		{
			if(voice_length_L!=0x00)
			voice_length_L=voice_length_L-1;
			else
			{										
				voice_length_h=voice_length_h-1;
				voice_length_L=0xff;	
			}
		}	
			
		if(controlcode==06)
		{
			if(Fg_FirstPCM12Data==0)
			{
				Fg_FirstPCM12Data=1;
				_Get_Send_Byte();
				voice_data_h=_acc;
				_Get_Send_Byte();
				voice_data_l=_acc;
			}
			else
			{
				Fg_FirstPCM12Data=0x00;	
				_Get_Send_Byte();				
				voice_data_h=_acc;
				GCC_SWAP(voice_data_l);		
			}
		}	
		break;
	default:				
		_Get_Send_Byte();
		controlcode=_acc;
		if(controlcode==0xff)
			Fg_Voice_END=1;	
		else
		{
			_Get_Send_Byte();
			voice_length_L=_acc;
			_Get_Send_Byte();
			voice_length_h=_acc;
		}
			
	}
	
}

void  _Get_Send_Byte(void)   
{	         
	_wcol=0;
	_trf=0;
	_simd=_acc;
	while (_wcol);
	while(!_trf);
	_acc=_simd;
}  