#pragma SMALL /* 预处理命令 */
//#pragma SRC
#i nclude
#i nclude
#define DTMF_STEP_TAB 0x200
#define DTMF_NO_TAB 0X210
#define DTMF_SIN_TAB 0x220
#define DAC_PORT P0
#define CBYTE ((char *)0x050000) //定义一个查表指针
//定义 名字 类型 0X05是查表区 0000是起始地址
// 1==idata
// 2==xdata
// 3==pdata
// 4==data
// 5==code
//DTMF OUTPORT
static unsigned char data H_step; //高频步长寄存器
static unsigned char data L_step; //低频步长寄存器
static unsigned char data H_ACC; //高频幅度寄存器
static unsigned char data L_ACC; //低频幅度寄存器
static unsigned char data H_DTMF; //高频频率寄存器
static unsigned char data L_DTMF; //低频频率寄存器
static unsigned char data DTMF_NO; //DTMF原码
static unsigned char data DTMF_NO_BUF; //DTMF原码寄存器
static unsigned char data DTMF_STATUS; //DTMF状态寄存器
static unsigned char data NO_ACC; //DTMF占用
static unsigned char data H_step_ACC; //高频步长累加寄存器
static unsigned char data L_step_ACC; //低频步长累加寄存器
static bit H_DEC; // ;高频组反向查表标志
static bit L_DEC; // ;低频组反向查表标志
static bit H_CPL; // ;高频组取反查表标志
static bit L_CPL; // ;低频组取反查表标志
static bit DTMF_SWITCH; // ;DTMF启动标志
DTMF();
void INTTTER0();
void TIMER0();
void INTTER1();
void TIMER1();
void series();
void TIMER2();
void main()
{
TCON=0x10;
TH1=255;
TL1=256-65;
EA=1;
TR1=1;
TF1=1;
for(;;)
DTMF();
}
void INTTTER0()interrupt 0
{
}
void TIMER0()interrupt 1
{
}
void INTTER1()interrupt 2
{
}
void TIMER1()interrupt 3
{
TR1=0;
TL1=256-65;
TH1=0xff;
TR1=1;
}
void series()interrupt 4
{
}
void TIMER2()interrupt 5
{
}
DTMF()
{
if (DTMF_SWITCH==0) goto DTMF_EXIT; //不允许输出则退出
if (DTMF_NO==DTMF_NO_BUF) goto SCANTAB; //DTMF号码未改则继续
DAC_PORT=0X80; //初始化输出口
DTMF_NO_BUF=DTMF_NO&0XF; //导入新数据
L_step_ACC=0; //清除数据区
H_step_ACC=0;
L_DEC=0; //清除标志位
H_DEC=0;
L_CPL=0;
H_CPL=0;
ACC=CBYTE[DTMF_NO_TAB+DTMF_NO_BUF]; //;查DTMF高低频率合成数据
NO_ACC=ACC;
H_DTMF=ACC&0XF; // ;分离高频数据
L_DTMF=NO_ACC>>4; //;分离低频数据
L_step=CBYTE[DTMF_STEP_TAB+L_DTMF]; //;求低频步长
H_step=CBYTE[DTMF_STEP_TAB+H_DTMF]; //;求高频步长
SCANTAB:
if (L_DEC==1) goto SUBTABL; //;转向反向查表
L_step_ACC=L_step_ACC+L_step; //步长累加
if (L_step_ACC<=144) goto continue_SCANL; //未超出由继续
L_step_ACC=144-(L_step_ACC-144); //超出就转反向扫描
L_DEC=1; //建立反向标志
goto continue_SCANL;
SUBTABL:
L_step_ACC=L_step_ACC-L_step;
if (L_step_ACC<=144) goto continue_SCANL; //;低频查表
L_step_ACC=256-L_step_ACC;
L_DEC=0;
L_CPL=!L_CPL;
continue_SCANL:
L_ACC=CBYTE[DTMF_SIN_TAB+L_step_ACC]+63; //求低频幅度
if (L_CPL==1) L_ACC=255-L_ACC; //结果取反
L_ACC&=0x7f; //修正
if (H_DEC==1) goto SUBTABH; //;转向反向查表
H_step_ACC=H_step_ACC+H_step;
if (H_step_ACC<=144) goto continue_SCANH;
H_step_ACC=144-(H_step_ACC-144);
H_DEC=1;
goto continue_SCANH;
SUBTABH:
H_step_ACC=H_step_ACC-H_step;
if (H_step_ACC<=144) goto continue_SCANH; //;高频查表
H_step_ACC=256-H_step_ACC;
H_DEC=0;
H_CPL=!H_CPL;
continue_SCANH:
H_ACC=CBYTE[DTMF_SIN_TAB+H_step_ACC]+63;
if (H_CPL==1) H_ACC=255-H_ACC; //结果取反
H_ACC&=0X7F;
DAC_PORT=H_ACC+L_ACC ; //;DTMF数据合成
DTMF_EXIT:
return;
}
TAB(){
#pragma asm
org DTMF_STEP_TAB
DB 26,29,32,35,45,50,55,61;
org DTMF_NO_TAB
DB 0X37,0X4,0X5,0X6,0X14,0X15,0X16,0X24,0X25;
DB 0X26,0X35,0X34,0X36,0X7,0X17,0X27;
org DTMF_SIN_TAB //;T=65/(δ=90/144=0.625)采样点的值
DB 0 ,1 ,1 ,2 ,3 ,3 ,4 ,5 ,5 ,6 ; //;0-9点
DB 7 ,8 ,8 ,9 ,10,10,11,12,12,13; //;10-19
DB 14,14,15,16,16,17,18,18,19,20; //;20-29
DB 20,21,22,22,23,23,24,25,25,26; //;30-39
DB 27,27,28,28,29,30,30,31,32,32; //;40-49
DB 33,33,34,34,35,36,36,37,37,38; //;50-59
DB 38,39,39,40,40,41,42,42,43,43; //;60-69
DB 44,44,45,45,46,46,46,47,47,48; //;70-79
DB 48,49,49,50,50,50,51,51,52,52; //;80-89
DB 52,53,53,53,54,54,55,55,55,56; //;90-99
DB 56,56,57,57,57,57,58,58,58,58; //;100-109
DB 59,59,59,59,60,60,60,60,60,61; //;110-119
DB 61,61,61,61,62,62,62,62,62,62; //;120-129
DB 62,62,62,63,63,63,63,63,63,63; //;130-139
DB 63,63,63,63,63; //;140-144
#pragma endasm
}
『本文转载自网络,版权归原作者所有,如有侵权请联系删除』