📄 kongwen120.c
字号:
//包含文件
#include <c8051f020.h>
#include <stdio.h>
#include <math.h>
#include <string.h>
#include <ctype.h>
#include <stdlib.h>
#include "F020_FlashPrimitives.h"
// 16-bit 特殊功能寄存器定义 'F02x
sfr16 DP = 0x82; // 数据指针
sfr16 TMR3RL = 0x92; // 定时器3,重装载数值寄存器
sfr16 TMR3 = 0x94; // 定时器3计数器
sfr16 ADC0 = 0xbe; // adc0数据
sfr16 ADC0GT = 0xc4; // adc0窗口比较器上限
sfr16 ADC0LT = 0xc6; // adc0窗口比较器下限
sfr16 RCAP2 = 0xca; // 定时器2捕捉/重装载
sfr16 T2 = 0xcc; // 定时器2
sfr16 RCAP4 = 0xe4; // 定时器4捕捉/重装载
sfr16 T4 = 0xf4; // 定时器4
sfr16 DAC0 = 0xd2; // DAC0 数据
sfr16 DAC1 = 0xd5; // DAC1 数据
// 函数原型
//*****************************************//
//************以下为系统函数*****************//
void main (void); //主函数
void sysclk_init (void); //系统时钟初始化函数
void port_init (void); //端口口初始化函数
void uart0_init (void); //串口初始化函数
void disable_dog(void); // 禁止看门狗
void init_dac1(void) ; //初始化dac1
void adc0_init (void); //初始化adc0
float temperature(unsigned char gain,unsigned int adc0_data); //温度测量函数
float get_temperature(void); //获得当前cpu温度
void delay_time(unsigned int time_value); //延时函数
void micro_init_dac1(void); //微动初始化dac1
void timer4_init (int counts); //定时器4初始化函数
void timer0_init(unsigned char counts); //定时器0初始化函数
void init_dac0(void);
void timer4_ISR (void); //定时器4中断子程序
void timer0_ISR(void); //定时器0中断子程序
void UART0_ISR (void); //接收中断
//*****************************************//
//*****************************************//
//************超级终端控制函数数*************/
void Tdata(char *str); //串口发送数据
void Tdatar(char s); //串口发送单个字符
char * trim(char * str); //去除字符串两边的空格
char atoii(char chr); //相当于c语言中的atoi函数
float atoff(char *); //相当于c语言中的atof函数
char * strstr1(char *,char *); //字符串查找命令//相当于c语言中的strstr函数
char strlen1(char *); //字符串长度命令//相当于c语言中的strlen函数
char * strcat1(char *,char *); //字符串合并命令//相当于c语言中的strcat函数
char * strmid(char * s,unsigned char begin,unsigned char longth);
//从字符串中取字符s:字符串指针,begin:开始位置,longth:要取的
void clr_datarx(void); //清除串口接收数组
char hwtanalyze(void); //系统内部自检
char *mysprint(float discode,unsigned char a1);//浮点数到字符串转换
#define atoffERROR 0 //atoff函数含非法字符返回错误标志
char uartflag; //记录本次串口是否接收完毕
char uartcount=0; //记录本次串口接收个数
xdata char *data_tx;
char display_flag=1; //显示标志,=0表示显示提示信息,=1表示不现实提示信息
unsigned char c_end[3]={13,10,0}; //回车换行字符串结束
char * lookresult; //通道命令解释时的辅助变量
char *lookresult1; //通道命令解释时的辅助变量
char *lookresult2; //通道命令解释时的辅助变量
char xdata array[100];
static char xdata data_rx[50]; //接收缓冲区
float xdata result1[200];
long xdata value_middle[5];
long xdata value_middle1[5];
long xdata value_middle2[5];
long xdata value_middle3[5];
long xdata value_middle4[15];
unsigned char eerom[32];
float get_real_value(unsigned char temp);
float xdata real_value[4];
float get_init_voltage(unsigned char channel);
unsigned char read_lcd();
void set_v_out(unsigned int voltage,unsigned char channel);
void FLASH_ByteWrite (FLADDR addr, char byte, bit SFLE);
unsigned char FLASH_ByteRead (FLADDR addr, bit SFLE);
void FLASH_PageErase (FLADDR addr, bit SFLE);
void adc0_single_init (unsigned char channel); //select adc channel
float get_bo_res(void);
float get_real_res(unsigned char temp);
float get_real_res_value(unsigned int temp,unsigned char channel);
float get_res_middle(unsigned char channel);
float get_v_middle(unsigned char channel);
float get_vdif_middle(unsigned char channel);
float get_res_diff(unsigned char channel);
void read_eerom(void);
void set_plot_address(unsigned char address);//设定CGRAM地址到地址计数器(AC);
void set_irram_address(unsigned char address);//SR=1:AC5-AC0为垂直卷动地址SR=0:AC3-AC0为ICON IRAM地址
void expend_cmd(unsigned char re,unsigned char g);//RE=1: 扩充指令集动作RE=0: 基本指令集动作
void set_shutdowm(unsigned char aa);//SL=1:脱离睡眠模式SL=0:进入睡眠模式
void reverse_video(unsigned char row);//选择4行中的任一行作反白显示,并可决定反白与否
void irram_curl(unsigned char temp);//SR=1:SR=0:
void wait_order(void); //将DDRAM填满"20H",并且设定DDRAM的地址计数器(AC)到"00H"
unsigned char read_ram(void);//从内部RAM读取资料(DDRAM/CGRAM/IRAM/GDRAM)
void write_ram(unsigned char temp_data);//写入资料到内部的RAM(DDRAM/CGRAM/IRAM/GDRAM)
unsigned char read_add_count(void);//读取同时可以读出位址计数器(AC)的值
unsigned char read_busy_flag(void);//功能:读取忙碌状态(BF)可以确认内部动作是否完成
void set_ddram(unsigned char address);//设定DDRAM地址到地址计数器(AC)
void set_cgram(unsigned char address);//功能:设定CGRAM位址到位址计数器(AC)
void cmd_set(unsigned char aa);//功能:DL=1(必须设为1) RE=1;扩充指令集动作 RE=0:基本指令集动作
void lcd_cursor_dis(unsigned char sc,unsigned char rl);//设定游标的移动与显示的移位控制位元;这个指令并不改变DDRAM的内容
void lcd_add_reset(void); //把DDRAM位址计数器调整为"00H",游标回原点,该功能不影响显示DDRAM功能:
//执行该命令后,所设置的行将显示在屏幕的第一行。显示起始行是由Z地址计数器控制的,
//该命令自动将A0-A5位地址送入Z地址计数器,起始地址可以是0-63范围内任意一行。
//Z地址计数器具有循环计数功能,用于显示行扫描同步,当扫描完一行后自动加一。
//指定在资料的读取与写入时,设定游标移动方向及指定显示的移位
void lcd_bit_add_reset(void); //把DDRAM位址计数器调整为"00H",游标回原点,该功能不影响显示DDRAM
void lcd_clear(void); //清除显示屏幕,把DDRAM位址计数器调整为"00H"
void lcd_swich(unsigned char d,unsigned char c,unsigned char b);//D=1;整体显示ON C=1;游标ON B=1;游标位置ON 后3位
void lcd_init(void);
void send_lcd_data(char *str);
void lcd_display(unsigned char page);
void set_dir_flag(unsigned char aa);
float average(void);
float average2(void);
//*****************************************//
//************以下是命令分析函数*************//
char help_an(); //帮助函数
void inchworm_init(void); //实际上是初始化dac0和dac1
//**********系统变量*************//
#define sysclk 22118400 // 系统时钟频率
#define BAUDRATE 9600 // 串口波特率
#define SAMPLE_RATE_DAC 80000L // DA采样频率
#define PHASE_PRECISION 65536 // 相位累加器
//*******************************************************//
//*******************************************************//
typedef struct robot //定义接收结构
{ //
unsigned char manner; //m
unsigned char base_value; //bv
unsigned int speed_left; //sl
unsigned int speed_right; //sr //sample period
unsigned int speed_rotate; //so
unsigned int robot_position; //sp
unsigned int delay_value; //dt
unsigned int v_out; //vo
unsigned int res0k; //k0
unsigned int res0b; //b0
unsigned int res1k; //k1
unsigned int res1b; //b1
unsigned int samples; //sa
unsigned int set_tem0; //t0
unsigned int set_tem1; //t1
unsigned int tem_v0; //v0
unsigned int tem_v1; //v1
}robot;
robot xdata robot1={1,10,5,200,10,1900,100,4000,9534,6588,9574,7229,400,150,150,3000,3000};
robot xdata robot2={1,10,5,200,10,1900,100,4000,9534,6588,9574,7229,400,150,150,3000,3000};
unsigned char go_stop=0; //运行变量
char robot_an(); //分析接收字符,判断处理
//*******************************************************//
//*******************************************************//
unsigned int frequency1 = 10; // 输出频率默认10
unsigned int frequency2=10; // 输出频率默认10
unsigned int phase_add1 = 10 * PHASE_PRECISION / SAMPLE_RATE_DAC; //全局累加相位1
unsigned int phase_add2=10* PHASE_PRECISION / SAMPLE_RATE_DAC; //全局累加相位2
//******************************//
//*******lcd位控制变量*************//sbit lcd_data1_cmd=P2^0;
sbit lcd_r1w=P2^1; //h,read
sbit lcd_en1_lach=P2^2;
sbit lcd_ps_select=P2^3; //h,prolell
sbit lcd_rst=P2^4;
sbit solid=P2^5;
sbit em0=P1^0;
sbit em1=P1^1;
sbit em2=P1^2;
sbit foot_sw=P3^2;
sbit emergy=P3^3;
unsigned long test_value_set=200000;
unsigned char repeat_value=0;
unsigned char get_id(void);
int xdata result[11];
int xdata testqqq[20];
float xdata q3=-153.1;
float xdata q2=874.2;
float xdata q1=2956.7;
unsigned int foot_acc=0,foot_acc1=0;
unsigned char foot_flag=0,tem0_flag=0,tem1_flag=0;
float xdata test_init_v[13];
float xdata regulator_v=0.240;
float get_regulator_v(unsigned char channel);
unsigned int sample_period=0;
float xdata temp_v[10];
float get_vdif(unsigned char channel);
float xdata first_v0=0.0,first_v1=0.0,second_v=0.0,repeat4_index=0.0,repeat4_index2=0.0;
float xdata tem_sample[5];
float xdata tem_sample2[5];
float xdata tem_avg2=0.0,tem_del_x2=0.0,tem_avg0=0.0,tem_del_x0=0.0;
unsigned char first_v_flag=0,repeat4_flag=0,tem_flag2=18,tem_flag0=18,control_flag=0,tem_sample_i=0,tem_sample_i2=0;
unsigned int tem_v_out1=0,tem_v_out0=0;
//**************************************************************************************//
//**************************************************************************************//
//主程序开始
void main(void)
{
float xdata temp_res=0.0,temp_tem=0.0;
float xdata temp_get1=0.0,temp_get2=0.0,temp_result1=0.0,temp_result2=0.0;
float xdata kk0=0.0,kk1=0.0,bb0=0.0,bb1=0.0;
unsigned int w=9;
long resistance=0;
unsigned long test=0;
unsigned char q_aa=0,q_bb=0;
int temp1=0;
disable_dog();
sysclk_init();
port_init();
adc0_init ();
init_dac1();
init_dac0();
q_aa=FLASH_ByteRead(4,1);
if(q_aa<220)
{
read_eerom();
}
tem_v_out0=3700-((int)robot1.set_tem0-126)*100/15;
tem_v_out1=3700-((int)robot1.set_tem1-126)*100/15;
for(q_bb=0;q_bb<5;q_bb++)
{
tem_sample[q_bb]=25.0; //后边程序能消除程序重新启动时带来的影响 在控制程序中
}
lcd_init();
lcd_clear();
lcd_display(1);
delay_time(3000);
lcd_display(2);
delay_time(3000);
set_dir_flag(0);
solid=0;
IP|=0x18;
// adc0_init ();
// init_dac1();
// init_dac0();
timer4_init(18400);
uart0_init ();
delay_time(200);
Tdatar(13);
Tdatar(10);
data_tx="欢迎使用泓鑫产品 045184322252";
Tdata(data_tx);
Tdatar(13);
Tdatar(10);
EA=1;
ES0=1;
uartflag=0;
repeat_value=4;
while(1)
{
if(uartflag)
{
w=robot_an();
uartflag=0;
}
if(repeat_value==1)
{
kk0=(float)robot1.res0k/10000;
bb0=(float)robot1.res0b/1000;
kk1=(float)robot1.res1k/10000;
bb1=(float)robot1.res1b/1000;
real_value[1]=0.0;
// temp1=(int)get_real_res_value(robot1.samples,0);
// resistance=(long)(temp1)*robot1.res0k/1000+robot1.res0b;
temp_get1=get_real_res_value(robot1.samples,0);
temp_result1=temp_get1*kk0+bb0;
temp1=(int)temp_result1;
data_tx="当前0通道电阻值 ";
Tdata(data_tx);
Tdata(mysprint(temp1,0));
data_tx=" 欧姆";
Tdata(data_tx);
Tdatar(13);
Tdatar(10);
temp_get2=get_real_res_value(robot1.samples,2);
temp_result2=temp_get2*kk1+bb1;
temp1=(int)temp_result2;
data_tx="当前1通道电阻值 ";
Tdata(data_tx);
Tdata(mysprint(temp1,0));
data_tx=" 欧姆";
Tdata(data_tx);
Tdatar(13);
Tdatar(10);
}
if(repeat_value==2)
{
T4CON=0;
q3=-1531000.0;
repeat_value=0;
real_value[1]=0.0;
resistance=(long)(temp1)*robot1.delay_value/100;
temp1=(int)resistance;
data_tx="当前电压值 ";
Tdata(data_tx);
Tdata(mysprint(temp1,0));
data_tx=" V";
Tdata(data_tx);
Tdatar(13);
Tdatar(10);
T4CON |= 0x04; // 启动定时器4
}
if(repeat_value==3)
{
if(temp_tem>=100.0)
{
set_ddram(0x8c);
send_lcd_data(mysprint(temp_tem,1));
}
else
{
set_ddram(0x8c);
data_tx=" ";
send_lcd_data(data_tx);
send_lcd_data(mysprint(temp_tem,1));
}
data_tx="当前温度值 ";
Tdata(data_tx);
Tdata(mysprint(temp_tem,1));
data_tx=" 度";
Tdata(data_tx);
Tdatar(13);
Tdatar(10);
// temp_res=get_real_res_value(robot1.samples,2);
// temp_result2=temp_res*kk1+bb1;
temp_result2=get_res_middle(2);
temp_tem=q1-100*pow(q2-q3*(1-temp_result2/1000),0.5); //计算温度值
if(temp_tem>=100.0)
{
set_ddram(0x8c);//need to modify
send_lcd_data(mysprint(temp_tem,1));
}
else
{
set_ddram(0x8c); //need to modify
data_tx=" ";
send_lcd_data(data_tx);
send_lcd_data(mysprint(temp_tem,1));
}
data_tx="当前温度值 ";
Tdata(data_tx);
Tdata(mysprint(temp_tem,1));
data_tx=" 度";
Tdata(data_tx);
Tdatar(13);
Tdatar(10);
// T4CON |= 0x04; // 启动定时器4
}
if(repeat_value==4)
{
if(repeat4_flag==0)
{
T4CON=0;
temp_result1=get_res_diff(0);
temp_result1=get_res_diff(0);
repeat4_index=q1-100*pow(q2-q3*(1-temp_result1/1000),0.5); //计算温度值
temp_result1=get_res_diff(2);
temp_result1=get_res_diff(2);
repeat4_index2=q1-100*pow(q2-q3*(1-temp_result1/1000),0.5); //计算温度值
repeat4_flag=1;
T4CON |= 0x04; // 启动定时器4
}
temp_result1=get_res_diff(0);
temp_tem=q1-100*pow(q2-q3*(1-temp_result1/1000),0.5); //计算温度值
if(fabs(repeat4_index-temp_tem)>2.0)
{
temp_tem=0.5*(temp_tem+repeat4_index);
repeat4_index=0.5*(temp_tem+repeat4_index);
}
if((temp_tem-tem_sample[0])>70) //能消除程序重新启动时带来的影响 在控制程序中
for(q_bb=0;q_bb<5;q_bb++)
{
tem_sample[q_bb]=temp_tem; //能消除程序重新启动时带来的影响 在控制程序中
}
tem_sample[tem_sample_i]=temp_tem;
if(tem_sample_i<5)
{
tem_sample_i++;
}
else
{
tem_sample_i=0;
}
tem_avg0=average();
tem_del_x0=(float)robot1.set_tem0-tem_avg0;
if(tem_del_x0>0)
{
tem_flag0=0;
}
if(tem_del_x0>0.3)
{
tem_flag0=1;
}
if(tem_del_x0>0.6)
{
tem_flag0=2;
}
if(tem_del_x0>0.9)
{
tem_flag0=3;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -