📄 clone.c
字号:
/*==========================================================================*/
/*
; SOURCE_FILE: Clone.C
; APPLICATION: LPC9XX
; COMPONENT: MAIN,KEY HANDER,INIT
; DATE: 16 May 2006
;
; (C) 2006 : CHANGHONG FPD SOFTWARE Lab
AUTHOR: DJ
*/
/*==========================================================================*/
#define _CLONE_C_
/* ======================================= */
// INCLUDE
/* ======================================= */
#include <REG922.H>
#include "define.h"
#include "clone.h"
#include "driver.h"
/* ======================================= */
//STATIC VARIABLE DEFINE
/* ======================================= */
static Bool bKeyDetect = FALSE;
static Byte DATA ucKeyValue = 0;
static Byte IDATA irSendBuffer[16];
static Word IDATA wWaitRecCount = 0;
static Byte IDATA ucWaitAckType = 0;
static Word IDATA wMainLoopCount = 0;
//static Byte IDATA temp_count = 0;
#ifdef DEBUG
static Byte IDATA uctest = 2;
#endif
/* ======================================= */
//FUNCTION DEFINE
/* ======================================= */
static Byte GetKeyValue(void)
{
Byte i = 10;
Byte keyValue;
keyValue = KEY_NONE;
EKBI = 1;
while(i--) ; //delay a moment
EKBI = 0;
if(g_bKBI)
{
g_bKBI = FALSE;
if(PIN_KEY1 == 0) //key1 pressed
keyValue = KEY_ACTION; /* Mod By dj 2006-10-25 */
else if(PIN_KEY2 == 0)
keyValue = KEY_FUNC_SEL;
else if(PIN_KEY3 == 0)
keyValue = KEY_RESET;
}
return(keyValue);
}
/* ======================================= */
static void KeyScan(void)
{
Byte count = 10;
Byte checkKeyValue;
ucKeyValue = GetKeyValue();
if(ucKeyValue == KEY_NONE) return;
else if(ucKeyValue == KEY_FUNC_SEL)
{
ucKeyValue = KEY_NONE;
if((g_ucCloneStatus == CLONE_NONE) ||
(g_ucCloneStatus == CLONE_SEND_PREPARE) ||
(g_ucCloneStatus == CLONE_REC_PREPARE))
{
while(count--)
{
Delay1ms(100);
ucKeyValue = GetKeyValue();
if(ucKeyValue == KEY_FUNC_SEL)
ucKeyValue = KEY_NONE;
else
return;
}
}
else
return;
ucKeyValue = KEY_FUNC_SEL;
}
else
{
while(count--) ;
checkKeyValue = GetKeyValue();
if(ucKeyValue != checkKeyValue) return;
}
bKeyDetect = TRUE;
}
/* ======================================= */
static void KeyHandler(void)
{
#ifdef DEBUG
Byte i;
#endif
if(bKeyDetect)
bKeyDetect = FALSE;
else return;
switch(ucKeyValue)
{
case KEY_FUNC_SEL:
if(g_ucCloneStatus == CLONE_NONE)
g_ucCloneStatus = CLONE_SEND_PREPARE;
else if(g_ucCloneStatus == CLONE_SEND_PREPARE)
g_ucCloneStatus = CLONE_REC_PREPARE;
else if(g_ucCloneStatus == CLONE_REC_PREPARE)
g_ucCloneStatus = CLONE_SEND_PREPARE;
break;
case KEY_ACTION:
#ifdef DEBUG
IRSend_16ByteData(irSendBuffer);
uctest++;
Delay1ms(200);
#else
if(g_ucCloneStatus == CLONE_SEND_PREPARE)
g_ucCloneStatus = CLONE_SEND_SEND_READY;
else if(g_ucCloneStatus == CLONE_REC_PREPARE)
g_ucCloneStatus = CLONE_SEND_REC_READY;
#endif
break;
case KEY_RESET:
#ifdef DEBUG
uctest = 2;
Delay1ms(100);
#else
GlobalVariableInit();
#endif
break;
default:
break;
}
ucKeyValue = KEY_NONE;
}
/* ======================================= */
static void GlobalVariableInit(void)
{
g_bIRDetect = FALSE;
g_bI2cError = FALSE;
g_bI2cOk = FALSE;
g_bKBI = FALSE;
g_ucIRRecDataType = REC_NONE;
g_ucCloneStatus = CLONE_NONE;
g_wCloneNVAddress = 0;
g_wTVNVAddress = CLONE_TV_NV_ADDR_START;
}
/* ======================================= */
/* ======================================= */
static void McuInit(void)
{
EA = 0;
/* ======================================= */
//PIN INIT
/*
PxM1.y PxM2.y Port output mode
0 0 Quasi-bidirectional
0 1 Push-pull
1 0 Input only (high impedance)
1 1 Open drain
P0-----KB0--KB7
P1-----RST,INT1,SDA,SCL,RXD,TXD
*/
P0 = 0x00;
P1 = BIT2+ BIT3 + BIT6;
//this pin open drain
P0M2 |= BIT0+ BIT6 + BIT7; // 3 led pin
P1M2 |= BIT2+ BIT3 + BIT6 + BIT7; //scl , sda , ir_out,led
//other pin ----Input only
/* ======================================= */
//IIC INIT
// EI2C = 1;
I2EN = 1;
AA = 1;
// CRSEL = 0;
I2SCLH = 25;
I2SCLL = 25;//70K about
/* ======================================= */
//INT priority
/*
IPxH IPx Interrupt priority level
0 0 Level 0 (lowest priority)
0 1 Level 1
1 0 Level 2
1 1 Level 3
*/
PT1 = 1;//timer 1 level 1
IP0H |= BIT2;//INT1 LEVEL 2 for ir rec //20060616
IP1 |= BIT0;
IP1H |= BIT0; //priority if the IIC is level 3
/* ======================================= */
//ADC INIT
/*
ADCON1 ENBI1 ENADCI1 TMM1 EDGE1 ADCI1 ENADC1 ADCS11 ADCS10 00 00000000
ADINS ADI13 ADI12 ADI11 ADI10 - - - - 00 00000000
ADMODA BNDI1 BURST1 SCC1 SCAN1 - - - - 00 00000000
ADMODB CLK2 CLK1 CLK0 - ENDAC1 - BSA1 - 00 000x0000
ADCON1 = 0x05;//Immediate Start mode. and Enable A/D channel 1.
ADINS = 0x20;//ADI11 key input
ADMODA = 0x10;//single conversion mode
ADMODB = 0x40;//adc clock is CCLK/3 = 2.46M
*/
/* ======================================= */
//TIMER INIT
ET1 = 1;//enable timer 1
TMOD = 0x11;// mode 1---16bit
WDCON &=0xE0; //Shut down WDT
/* ======================================= */
//EXTERAL INTERRUPT
EX1 = 1;
IT1 = 1;
/* ======================================= */
//KBI INIT
KBMASK = BIT1 + BIT2 + BIT3;
EA = 1; //enable all interrupt
}
/* ======================================= */
Byte CalculateCheckSum(Byte DataNum,Byte *pbuffer)
{
Byte i;
Word TempSum = 0;
for(i = 0;i < DataNum;i++)
{
TempSum += *pbuffer;
pbuffer++;
}
return((Byte)TempSum);
}
/* ======================================= */
static Bool VerifyCheckSum(CHECK_SUM_TYPE type)
{
Byte temp;
switch(type)
{
case CHECK_ADDRESS:
if(CalculateCheckSum(2,&irRecBuffer[2]) == irRecBuffer[4])
return(TRUE);
break;
case CHECK_N_BYTE:
temp = irRecBuffer[2];//data byte numbers
if(CalculateCheckSum(temp,&irRecBuffer[3]) == irRecBuffer[temp + 3])
return(TRUE);
break;
case CHECK_16_BYTE:
if(CalculateCheckSum(16,&irRecBuffer[2]) == irRecBuffer[18])
return(TRUE);
break;
default:
break;
}
return(FALSE);
}
/* ======================================= */
static Bool CheckRecAck(WAIT_ACK_TYPE type)
{
switch(type)
{
case SEND_SENDREADY_WAITACK:
if(g_ucIRRecDataType == REC_REC_READY)//get ack
{
g_ucCloneStatus = CLONE_SEND_DATA;
g_wTVNVAddress = CLONE_TV_NV_ADDR_START;
g_wCloneNVAddress = 0;
return(TRUE);
}
break;
/*
case SEND_ADDRESS_WAITACK:
if(g_ucIRRecDataType == REC_REC_READY)//get ack
{
g_ucCloneStatus = CLONE_SEND_DATA;
return(TRUE);
}
break;
*/
case SEND_DATA_WAITACK:
if(g_ucIRRecDataType == REC_REC_READY)//get ack
{
if(g_wTVNVAddress > CLONE_TV_NV_ADDR_END)
{
g_ucCloneStatus = CLONE_SEND_END;
}
else
{
g_ucCloneStatus = CLONE_SEND_DATA;
}
return(TRUE);
}
break;
case SEND_RECREADY_WAITACK:
if(g_ucIRRecDataType == REC_SEND_READY)
{
IRSend_RecReady();
CloneStatusToRecData();
return(TRUE);
}
break;
default:
break;
}
return(FALSE);
}
/* ======================================= */
static void CloneStatusToWaitACK(WAIT_ACK_TYPE type)
{
g_ucCloneStatus = CLONE_WAIT_ACK;
ucWaitAckType = type;
wWaitRecCount = 0;
}
/* ======================================= */
static void CloneStatusToRecData(void)
{
g_ucCloneStatus = CLONE_REC_AND_SEND_ACK;
g_wCloneNVAddress = 0;
g_wTVNVAddress = CLONE_TV_NV_ADDR_START;
wWaitRecCount = 0;
}
static void CloneStatusToSendData(void)
{
g_ucCloneStatus = CLONE_SEND_DATA;
g_wTVNVAddress = CLONE_TV_NV_ADDR_START;
g_wCloneNVAddress = 0;
}
/* ======================================= */
static void CloneClearRecMessage(void)
{
/*
Byte i;
for(i = 0;i < 19; i++)
{
irRecBuffer[i] = 0;
}
*/
//clear the flag
g_ucIRRecDataType = REC_NONE;
g_bIRDetect = 0;
wWaitRecCount = 0;
}
/* ======================================= */
static void CloneHandler(void)
{
#ifdef DEBUG
if(g_bIRDetect)
{
g_bIRDetect = 0;
g_wCloneNVAddress = 0;
NVWriteNByte(16, &irRecBuffer[2]);
}
#else
// Byte i;
// Word RecNVAddress;
Byte num;
if(g_ucCloneStatus == CLONE_NONE) return;
switch(g_ucCloneStatus)
{
//process send data
case CLONE_SEND_SEND_READY:
IRSend_SendReady();
Delay1ms(120);
CloneStatusToSendData();
break;
/*
case CLONE_SEND_ADDR:
IRSend_Address(g_wTVNVAddress);
CloneStatusToWaitACK(SEND_ADDRESS_WAITACK);
break;
*/
case CLONE_SEND_DATA:
if(g_wTVNVAddress <= (CLONE_TV_NV_ADDR_END - 15))//send 16 byte data
{
NVReadNByte(16,irSendBuffer);
IRSend_16ByteData(irSendBuffer);
g_wTVNVAddress += 16;
g_wCloneNVAddress += 16;
}
else if(g_wTVNVAddress <= CLONE_TV_NV_ADDR_END)//send n byte data
{
num = CLONE_TV_NV_ADDR_END - g_wTVNVAddress + 1;
NVReadNByte(num, irSendBuffer);
IRSend_nByteData(num,irSendBuffer);
g_wTVNVAddress += num;
}
// CloneStatusToWaitACK(SEND_DATA_WAITACK); //20061008 del 子机不回复ACK,等待100ms后继续发
Delay1ms(120);
if(g_wTVNVAddress > CLONE_TV_NV_ADDR_END) //数据发送完毕
{
g_ucCloneStatus = CLONE_SEND_END;
}
break;
//recevie data handle
case CLONE_SEND_REC_READY:
IRSend_RecReady();
CloneStatusToWaitACK(SEND_RECREADY_WAITACK);
break;
case CLONE_REC_AND_SEND_ACK:
/*
if(g_ucIRRecDataType == REC_DATA_ADDRESS)
{
RecNVAddress = (irRecBuffer[2] << 8) + irRecBuffer[3];
if((RecNVAddress == g_wTVNVAddress) &&
VerifyCheckSum(CHECK_ADDRESS))
{
IRSend_RecReady();
}
else
{
g_ucCloneStatus = CLONE_ERROR;
}
}
*/
if(g_bIRDetect)
{
if(g_ucIRRecDataType == REC_16_BYTES)
{
if(VerifyCheckSum(CHECK_16_BYTE))
{
NVWriteNByte(16, irRecBuffer + 2);
g_wTVNVAddress += 16;
g_wCloneNVAddress += 16;
IRSend_RecReady();
}
else
{
g_ucCloneStatus = CLONE_CHECKSUM_ERROR;
}
}
else if(g_ucIRRecDataType == REC_N_BYTES)
{
if(VerifyCheckSum(CHECK_N_BYTE))
{
num = irRecBuffer[2];//N bytes number
NVWriteNByte(num, &irRecBuffer[3]);
g_wTVNVAddress += num;
g_wCloneNVAddress += num;
IRSend_RecReady();
}
else
{
g_ucCloneStatus = CLONE_CHECKSUM_ERROR;
}
}
else
{
g_ucCloneStatus = CLONE_REC_CUSTOM_ERROR;
}
if(g_wTVNVAddress > CLONE_TV_NV_ADDR_END)
{
g_ucCloneStatus = CLONE_REC_END;
}
CloneClearRecMessage();
}
else if(++wWaitRecCount > 30000)
g_ucCloneStatus = CLONE_ERROR;
break;
case CLONE_WAIT_ACK:
if(g_bIRDetect)
{
if(!CheckRecAck(ucWaitAckType))
{
g_ucCloneStatus = CLONE_ERROR;
}
CloneClearRecMessage();
}
else if(++wWaitRecCount > 30000)
g_ucCloneStatus = CLONE_ERROR;
break;
//add for remote receive data from another remote
case CLONE_REC_PREPARE:
if(g_bIRDetect)
{
if(g_ucIRRecDataType == REC_SEND_READY)
{
IRSend_RecReady();
CloneStatusToRecData();
}
CloneClearRecMessage();
}
break;
case CLONE_SEND_END:
IRSend_IrEnd();
GlobalVariableInit();
break;
case CLONE_REC_END:
GlobalVariableInit();
break;
default:
break;
}
#endif
}
/* ======================================= */
static void LedDisplayHandler(void)
{
#ifdef DEBUG
if(g_bI2cError)
{
if((wMainLoopCount % 1000) == 0) //fast blink
All_LED_Blink();
}
else if(g_ucIRRecDataType == REC_ERROR)
{
All_LED_On();
}
else
#endif
{
switch(g_ucCloneStatus)
{
case CLONE_NONE:
LED1_On_Only();
break;
/* 发送 */
case CLONE_SEND_PREPARE:
LED3_On_Only();
break;
case CLONE_SEND_SEND_READY:
case CLONE_SEND_DATA:
LED3_Blink_Only();
break;
/* 接收 */
case CLONE_REC_PREPARE:
LED2_On_Only();
break;
case CLONE_SEND_REC_READY:
case CLONE_REC_AND_SEND_ACK:
if((wMainLoopCount % 1500) == 0) //slow blink
{
LED2_Blink_Only();
}
break;
#ifdef DEBUG
case CLONE_ERROR:
if((wMainLoopCount % 1000) == 0) //fast blink
{
LED4_Blink_Only();
}
break;
case CLONE_REC_CUSTOM_ERROR:
if((wMainLoopCount % 1000) == 0) //fast blink
{
LED3Blink();
LED4Blink();
}
break;
case CLONE_CHECKSUM_ERROR:
if((wMainLoopCount % 1000) == 0) //fast blink
{
LED1Blink();
LED2Blink();
}
break;
#else
case CLONE_ERROR:
case CLONE_REC_CUSTOM_ERROR:
case CLONE_CHECKSUM_ERROR:
if((wMainLoopCount % 1000) == 0) //fast blink
{
LED4_Blink_Only();
}
break;
#endif
default:
break;
}
}
}
void main(void)
{
SP = 0x60;
//Initial
McuInit();
GlobalVariableInit();
//main loop
while(1)
{
// if((wMainLoopCount % 160) == 0)//about 16ms /* Del By dj 2006-10-16 */
{
KeyScan();
KeyHandler();
}
IR_CheckLeadingHander();
CloneHandler();
LedDisplayHandler();
wMainLoopCount++;
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -