⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ze015_1._c

📁 一款完整的家用电器程序,具有控制商用机的功能,应用广泛,有一定的参考价值
💻 _C
📖 第 1 页 / 共 2 页
字号:
//ICC-AVR application builder : 2007-4-11 16:34:42
// Target : M64
// Crystal: 4.0000Mhz

#include <iom64v.h>
#include <macros.h>
#include <math.h>
#include  "jf_atmel.h"
#include  "jf_valve.h"
#include  "jf_p1.c"
#include  "jf_act.c"
#include  "jf_valve.c"



void port_init(void)
{
 PORTA = 0x00;
 DDRA  = 0x0F;//0x0b;		//sck PA0-CD4052A,PA1-CD4052B
 PORTB = 0x00;
 DDRB  = 0xF0;
 PORTC = 0x00; //m103 output only
 DDRC  = 0x01;
 PORTD = 0x00;
 DDRD  = 0xFB;
 PORTE = 0x00;
 DDRE  = 0xC6;
 PORTF = 0x00;
 DDRF  = 0x00;
 PORTG = 0x00;
 DDRG  = 0x1B;
}

//Watchdog initialize
// prescale: 16K 
void watchdog_init(void)
{
WDR(); //this prevents a timout on enabling
 WDTCR |= 0x18;	//允许修改watchdog
 //WDTCR = 0x0d; //WATCHDOG ENABLED - 101--0.45s
 WDTCR = 0x0e; //WATCHDOG ENABLED - 110--1s
}

//TIMER0 initialize - prescale:1024
// WGM: Normal
// desired value: 10mSec
// actual value:  9.984mSec (0.2%)
void timer0_init(void)
{
 TCCR0 = 0x00; //stop
 ASSR  = 0x00; //set async mode
 TCNT0 = 0x83;  //4MHZ-8ms set count
 OCR0  = 0x7D;
 TCCR0 = 0x06; //start timer
}

#pragma interrupt_handler timer0_ovf_isr:17
void timer0_ovf_isr(void)
{
 TCNT0 = 0x83;//64; //reload counter value
 time_flag |=b_time_10ms;	//f_10ms=1
  t_10ms_times++;  //10ms时间计时 	     
 if (t_10ms_times>=12)
 	{
 		time_flag |=b_time_100ms; //f_100ms=1
 		t_10ms_times=0;
 	}
 if (mode & b_fast_test)time_flag |=b_time_1s;	//快测f_1s=1
 else
 {//正常时计数100时置1秒
 	t_1s_times++;	//10ms的计时1秒
 	if (t_1s_times>=125)
 	{
 		time_flag |=b_time_1s; //f_1s=1
 		t_1s_times=0;
 	}
 }
 if (run_state &b_beep_onask)	//01-beep_on
    {	//蜂鸣器要求响时,时间进行计数,计数到则关T2的CTC
	 	if (beep_time >=beep_time_ask) 
		 {//蜂鸣器响时间到时停止TIMER2,如次数未到则启动间隔计时
		 	PORTB &=~b_beep;	//beep=0 PB5时间到则关蜂鸣器
		 	TCCR2 = 0x00; //stop T2 CTC
		 	run_state &=~b_beep_onask;	//清除蜂鸣器响标志
		 	if (beep_times >=1)  //如果要求响的次数大于1
		 	  {
		 		beep_times--;	// 蜂鸣器响的次数-1
		 		auto_state |=b_beep_stop;	//开始蜂鸣器停止的间隔计时
		 		beep_stop_time =0;	//间隔计时清0
		 	  }  
		 	  
		  }
		else beep_time++;//蜂鸣器响时间未到时接着响,蜂鸣器响时间+1
	} 	
  else if (auto_state &b_beep_stop)
  	{//蜂鸣器间隔计时,计时到时启动TIMER2为CTC
  		beep_stop_time ++;	//间隔计时+1
  		if (beep_stop_time >=beep_stop_time_ask)
  			{//蜂鸣器间隔计时到时启动TIMER2
  				TCCR2 = 0x00; //stop
				 TCNT2 = 0x87; //0x86; // 2048 Khz    0x83; //2khz
				 OCR2  = 0x79; //0x7a; //0x7d;
				 TCCR2 = 0x1A; //start
  				beep_time=0; //蜂鸣器响时间=0
  				auto_state &=~b_beep_stop;	//清间隔计时标志
  				run_state |=b_beep_onask;	//蜂鸣器响标志
  			}
  	}
  else	
  {//无蜂鸣器响或间隔要求时关T2,输出0
  	TCCR2 = 0x00; //stop T2 CTC
  	PORTB &=~b_beep;	//beep=0 PB5时间到则关蜂鸣器
  }
//uart0 与主模块板通讯,等待主模块,接收正确后延时40MS发送应答,发送完成后立即转接收
 if (txd_state0 &rxd_txdstart0)	//rxd_txdstart=1
 	{
	txd_rxd_delaytime0++;
	if (txd_rxd_delaytime0>=5)	//接收完成转发送时延时40ms
	   {
		PORTE |= b_con4850;	//pe2为uart0-485控制端=1 txd
 		UCSR0B = 0x48;	// uart0_txd_on允许发送完成中断及发送
		txd_state0 &= ~rxd_txdstart0;	//rxd_txdstart=0
		txd_rxd_delaytime0=0;
		txd_len0=0;
		UDR0 =txd_data0[txd_len0];//每隔1秒写入第1个数据发送	
		txd_len0++;
		}
	}
		m_32mscountv=m_32mscountv+1;
		m_500mscount=m_500mscount+1;
}

//TIMER1 initialize - prescale:64
// WGM: 0) Normal, TOP=0xFFFF
// desired value: 1Hz
// actual value:  1.000Hz (0.0%)
void timer1_init(void)
{
 TCCR1B = 0x00; //stop
 TCNT1H = 0x0B; //setup
 TCNT1L = 0xDC;
 OCR1AH = 0xF4;
 OCR1AL = 0x24;
 OCR1BH = 0xF4;
 OCR1BL = 0x24;
 OCR1CH = 0xF4;
 OCR1CL = 0x24;
 ICR1H  = 0xF4;
 ICR1L  = 0x24;
 TCCR1A = 0x00;
 TCCR1B = 0x03; //start Timer
}

#pragma interrupt_handler timer1_ovf_isr:15
void timer1_ovf_isr(void)
{//20080201将定时1秒改在定时10MS中,增加快测
 //TIMER1 has overflowed 1s 1秒定时
	 TCNT1H = 0x0b; //reload counter high value
	 TCNT1L = 0xdc; //reload counter low value
 //20080201time_flag |=b_time_1s;	//f_1s=1
}
//TIMER2 initialize - prescale:8 中断未用,但用作蜂鸣器驱动2KHZ
// WGM: CTC
// desired value: 4KHz
// actual value:  3.992KHz (0.4%)
void timer2_init(void)
{
 TCCR2 = 0x00; //stop
 TCNT2 = 0x87; //0x86; // 2048 Khz    0x83; //2khz
 OCR2  = 0x79; //0x7a; //0x7d;
}

#pragma interrupt_handler timer2_ovf_isr:11
void timer2_ovf_isr(void)
{//no use but remain,定时器2用途CTC蜂鸣器驱动
 TCNT2 = 0x06;  //reload counter value
}
//TIMER3未用 
//TIMER3 initialize - prescale:256
// WGM: 0) Normal, TOP=0xFFFF
// desired value: 100mSec
// actual value: 100.000mSec (0.0%)
void timer3_init(void)
{
 TCCR3B = 0x00; //stop
 TCNT3H = 0x0B; //setup
 TCNT3L = 0xDC;
 OCR3AH = 0xF4;
 OCR3AL = 0x24;
 OCR3BH = 0xF4;
 OCR3BL = 0x24;
 OCR3CH = 0xF4;
 OCR3CL = 0x24;
 ICR3H  = 0xF4;
 ICR3L  = 0x24;
 TCCR3A = 0x00;
// TCCR3B = 0x03; //start Timer
TCCR3B = 0x00;
}

#pragma interrupt_handler timer3_ovf_isr:30
void timer3_ovf_isr(void)
{//no use 
 //TIMER3 has overflowed
 TCNT3H = 0x0b; //reload counter high value
 TCNT3L = 0xdc; //reload counter low value
}

//UART0 initialize
// desired baud rate: 9600
// actual: baud rate:9615 (0.2%)
void uart0_init(void)
{
 UCSR0B = 0x00; //disable while setting baud rate
 UCSR0A = 0x00;
 UCSR0C = 0x06;
 UBRR0L = 0x19; //set baud rate lo
 UBRR0H = 0x00; //set baud rate hi
  UCSR0B = 0x90;	// uart0_rxd_on允许接收完成中断及接收
  PORTE &= ~b_con4850;	//pe2为uart0 485控制端=0接收
}

#pragma interrupt_handler uart0_rx_isr:19
void uart0_rx_isr(void)
{
 //串行口0用作与显示板按7E7E商用通讯格式,接收到显示板ID01及点名02后回复
 unsigned	char	m,n;
	m =UCSR0A;
	n =UDR0;
	if ((m &0x1C)==0)	//UCSRA中是否有接收出错(帧错、校验错、溢出错)
	{//接收正常
		switch (rxd_state0)
		{
		case 0x00:	//接收头码7EH
			{
			if (n==0x7E) 
			{rxd_state0=0x01;rxd_good0=0;}
			else  rxd_state0=0x00;	//出错时重新开始接收
			break;
			}
		case 0x01:	//接收头码7EH
			{
			if (n==0x7E) 
				{rxd_state0=0x02;}
			else rxd_state0=0x00;	//出错时重新开始接收
			break;
			}
		case 0x02:	//接收地址address;	//本机地址
			{
			if (n==0x40) //20080201  if (n==address)
				{
					rxd_state0=0x03;
					rxd_checksum0=n;	//异或校验码初始值
				}	
			else 
				{if (n==0x7E) rxd_state0=0x02;	//接收到7EH为头码1
				else rxd_state0=0x00;	//出错时重新开始接收
				}
			break;
			}
		case 0x03:	//接收发送方T_addr==0xff,其它出错
			{
			T_addr =n;	//发送方T_addr
			if (n==0xff) 
				{
					rxd_state0=0x04;
					rxd_checksum0^=n;	//异或校验
				}
			else 
				{if (n==0x7E) rxd_state0=0x01;	//接收到7EH为头码1
				else rxd_state0=0x00;	//出错时重新开始接收
				}
			break;
			}	
		case 0x04:	//接收包号0x11
			{
			if (n==0x11) 
				{
					rxd_state0=0x05;rxd_len0=0;
					rxd_checksum0^=n;	//异或校验
				}
			else 
				{if (n==0x7E) rxd_state0=0x01;	//接收到7EH为头码1
				else rxd_state0=0x00;	//出错时重新开始接收
				}
				break;
			}
		case 0x05:	//接收长度<=48
			{
			if (n<=0x30)
				{
					rxd_state0=0x06;rxd_len0_ask=n;rxd_data0[rxd_len0]=n;
					rxd_len0++;rxd_checksum0^=n;	//异或校验
				}
			else 
				{if (n==0x7E) rxd_state0=0x01;	//接收到7EH为头码1
				else rxd_state0=0x00;	//出错时重新开始接收
				}
			break;
			}
		case 0x06:	//接收IDH
			{
			   rxd_state0=0x07;rxd_data0[rxd_len0]=n;
			   rxd_checksum0^=n;rxd_len0++;
				break;
			}
		case 0x07:	//接收IDL
			{
			   rxd_state0=0x08;rxd_data0[rxd_len0]=n;
			   rxd_checksum0^=n;rxd_len0++;
				break;
			}					
		case 0x08:	//接收命令字
			{
			if (n<=0x0f)
			   {rxd_state0=0x10;rxd_command0=n;rxd_data0[rxd_len0]=n;
			   rxd_checksum0^=n;rxd_len0++;}
			else 
				{if (n==0x7E) rxd_state0=0x01;	//接收到7EH为头码1
				else rxd_state0=0x00;	//出错时重新开始接收
				}
				break;
			}	
		
		case 0x10:	//接收数据
			{
			if (rxd_len0 <rxd_len0_ask)
				{rxd_data0[rxd_len0]=n;rxd_checksum0^=n;rxd_len0++;}
			else 
			   {
				if (rxd_checksum0==n) fun_rxdgood0();	//接收正确处理程序
				else	
				   {if (n==0x7E) rxd_state0=0x01;	//接收到7EH为头码1
					else rxd_state0=0x00;	//出错时重新开始接收
				   }
			    }	
			break;
			}	
		}
	}
}

void fun_rxdgood0(void )	//接收正确处理程序
   {
	unsigned    char   i ;
	rxd_nogood_time=0; //通讯故障连续时间=0
	 if (rxd_command0==0x01)  //ID号命令
	    {
	    	fun_txddata0_ID();	  //ID号命令
	    }
	 else  
	 {
	 	if ((mode & b_urgent)==0) 
		  {//在应急状态下,触摸屏或显示板的开关机及手动命令\设置参数无效
		 	if ((rxd_command0==0x02) &&(rxd_len0==26))fun_rxd_data0(); //接收主板点名
		  }
	 	fun_txd_data0();	//发送应答主板点名的数据
	  }
	  if ((fault_tongxun_times<6) &&((fault_state2 &b_fault_tongxun)!=0))	//通讯故障次数
	  {//
	  	if ((rxd_command0==0x02) &&(rxd_len0==26))
	  	{//三次内如正确接收到主模块板的点名,则清除故障
	  		fault_state2 &=~b_fault_tongxun;	
	  		}
	  }
   }    
    
 void fun_rxd_data0(void )	//存入显示板点名的数据 
    {
	unsigned    char   i ,temp;
	unsigned    char  *point_temp;
	point_temp = &rxd_data0[4];	//i=4;	//第1个有效数据
	int_THset= *point_temp++; //字节1设定温度整数
 	RHset=*point_temp++; //字节2设定湿度整数
 //字节3高4位为设定温度小数,低4位为湿度精度RHm2~10,出厂设置5
  	dig_THset =*point_temp>>4; 
  	rh_actual =*point_temp &0x0f;
  	point_temp++;
  	th_actual10=*point_temp++; //字节4温度精度Tm 0.5~5,出厂设置*10
  	i_cof_sensiadj10=*point_temp++;	//字节5灵敏度调节参数*10
  	i_adj_time=*point_temp++;	//字节6容调间隔时间秒
	mode_set_1=*point_temp++; //字节7模块组合参数
   	mint_comprun_set=*point_temp++;	//字节8压缩机最小运行时间1~6分钟
  	imax10_set=*point_temp++;	//字节9加湿器额定电流*10
  	t_outpai_set=*point_temp++;	//字节10加湿器定时排水时间5~120秒,出厂设置60秒
  	humid_ratio=*point_temp++;	//字节11加湿器量设定%
  	exghaust_TH_set=*point_temp++;	//字节12排气温度保护
  	mint_compstop_set=*point_temp++; //字节13压缩机最小停机时间1~6分钟
  	t_fan_ondelay_set=*point_temp++; //字节14送风机延时启动时间出厂设置5秒
  	temp=*point_temp++; //字节15压缩机延时启动时间 1分钟=3*20秒
  	t_comp_ondelay_set =temp+temp+temp;	//20080114将接收到的压缩机延时启动时间转成20秒
  	t_lppdelay_set=*point_temp++;	//字节16低压保护延时出厂设置20秒
  	rh_value_modify=*point_temp++;	//字节17回风湿度修正值负数
  	th_value_modify=*point_temp++;	//字节18回风温度修正值负数*10
  	act_ask_set=*point_temp++; //字节19动作请求
	manual_act_ask =act_ask_set;	//置手动设置
	mokuai_set=*point_temp++; //字节20模块模式 //字节21\22预留字节
	if (mokuai_set &b_fault_rst_onask)run_state2 |=b_fault_reset;	//故障复位命令
//	if ((mokuai_set &b_connect_onask) &&(mokuai_set &b_kaiji_ask)) mode |=b_kaiji;	//当模块连接及开机时为开机,断开时为关机
	if (mokuai_set &b_kaiji_ask) mode |=b_kaiji;	//20080107当模块开机时为开机,关机时为关机,
	else mode &=~b_kaiji;
	if (mokuai_set &b_manual_onask) mode |=b_manual_on;	//当模块手动时为手动
	else mode &=~b_manual_on;	//自动,备用先不管
	NOP();	//先不管显示板控制有效,都认故障复位命令 TEST
	humid_rated=*point_temp++;//字节21额定加湿量设定
	fault_yuliu=*point_temp;//字节2220071115数据11预留 主模块故障标志 B7
   }
   
void fun_txd_data0(void)	//发送子模块板的运行数据
  {
	signed    char   temp ;//暂存值
	unsigned    char   temp_txd ;//发送数据
	unsigned    char   temp_checksum ;//校验
	unsigned    char  *point_txd;
	 point_txd = &txd_data0[0];
	 *point_txd++ =0x7E;
	 *point_txd++=0x7E;
	 *point_txd=0xFF;	//显示板接收方为FFH
	 temp_checksum=*point_txd++;	//异或校验
	 *point_txd =0x40;	//20080201 address;	//发送方地址
	 temp_checksum ^=*point_txd++;	//异或校验
	 *point_txd=0x11;	//包号
	 temp_checksum ^=*point_txd++;	//异或校验
	 *point_txd=26;	//长度26
	 temp_checksum ^=*point_txd++;	//异或校验	 
	 *point_txd=ID_l;	//IDH机组ID号
	 temp_checksum ^=*point_txd++;	//异或校验
	 *point_txd=ID_h;	//IDl机组ID号
	 temp_checksum ^=*point_txd++;	//异或校验
	*point_txd=0x82;	//回复显示板点名机组命令82H
	 temp_checksum ^=*point_txd++;	//异或校验
	 temp=t_value10_20s>>8;	//数据1回风温度高8位
	 *point_txd=temp;
	 temp_checksum ^=*point_txd++;	//异或校验
	 *point_txd=(unsigned char)(t_value10_20s);	//数据2回风温度的低8位
	 temp_checksum ^=*point_txd++;	//异或校验
	 *point_txd=rh_value_20s;	//数据3回风湿度平均值
	 temp_checksum ^=*point_txd++;	//异或校验
	 *point_txd=i_humid10;	//数据4加湿电流*10
	 temp_checksum ^=*point_txd++;	//异或校验
	 *point_txd=exghaust_TH;	//数据5压缩机排气温度EXHAUST
	 temp_checksum ^=*point_txd++;	//异或校验
	*point_txd=act_state1;//数据6输出1

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -