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

📄 ade7758.c

📁 实现对ADE7758电能芯片的读写和校准,8051单片机,通过PC对电参量进行校准
💻 C
📖 第 1 页 / 共 4 页
字号:
				data_segment_flag =  read_iap( FLASH_START_ADD + i );
				break;
			}
		}
		else
		break;
	}//end of while()
	

	EA = 1;
	
}//end of void look_for_flag()

/*************************************************************************************
                                 写数据段标记
在将数据保存到FLASH之前必须先确定数据将存放在那一个数据段
**************************************************************************************/
sbit rec_led  = P3^6;
sbit trx_led  = P3^7;

void write_data_flag()// using 2
{
	uchar temp;
	
	//EA = 0;
	if( data_segment_flag == (DATA_TABLE_LEN - 1) )//已经到了最后一个数据段,必须将整个数据段擦除
	{
	
		EA = 0;
		erase_flash();
		data_segment_flag = 0xff;
		EA = 1;
	}
	//////////////////////////////
	if( data_segment_flag != 0xff )
	{
		data_segment_flag += 1;
		temp = write_iap( data_segment_flag ,FLASH_START_ADD + data_segment_flag );
	}
	else
	{//以前没有数据标志
		data_segment_flag = 0;
		temp = write_iap( 0,FLASH_START_ADD + 0 );
		

	} 
	////////////////////////////////

	EA = 1;
}//end of void write_data_flag()


/************************************************************************************

将数据存放到FLASH中,每一次掉电存放一个区,区长度为100字节,存放150次后重新从头存过

*************************************************************************************/

void save_en_to_flash() using 2 //将数据存到MCU的FLASH存储器中
{
	uchar idata i,j;
	uchar idata temp_data;
	uchar idata temp_add = 0;
	uint  idata segment_address;
	//EA = 0;
	//////////////////////////////////////////////////////////////////
	/*
	if(data_segment_flag == 0xff)
	{
		rec_led = 0;
		return;
	}*/
	//////////test
	segment_address = DATA_START + (uint)data_segment_flag * DATA_SEGMENT_LEN;
	
	temp_data = write_iap( SAVE_OK , segment_address );

	//the part of "kwh" 
	for(i = 0; i < 3 ; i++)
	{
		for( j = 0; j < 4 ; j++)
		{
			temp_add++;
			
			//temp_data = rwdata.working.watt_hour[i].data8[j];
			
			//write_iap( temp_data , segment_address + temp_add );
			write_iap( rwdata.working.watt_hour[i].data8[j] , segment_address + temp_add );
		}//end of for(j)
	}//end of for(i)
	
	for(i = 0; i < 3 ; i++)
	{
		for( j = 0; j < 4 ; j++)
		{
			temp_add++;
			
			//temp_data = rwdata.working.var_hour[i].data8[j];
			
			//write_iap( temp_data , segment_address + temp_add );
			write_iap( rwdata.working.var_hour[i].data8[j], segment_address + temp_add );
		}//end of for(j)
	}//end of for(i)
	
	for(i = 0; i < 3 ; i++)
	{
		for( j = 0; j < 4 ; j++)
		{
			temp_add++;
			
			//temp_data = rwdata.working.va_hour[i].data8[j];
			
			//write_iap(temp_data , segment_address + temp_add );
			write_iap(rwdata.working.va_hour[i].data8[j] , segment_address + temp_add );
		}//end of for(j)
	}//end of for(i)
	
	temp_data = write_iap( SAVE_OK , segment_address + 90);//test
	
	//the part of "ws"
	for( i = 0; i < 9; i++)
	{
		for( j = 0; j < 4; j++)
		{
			temp_add++;
			
			//temp_data = energy[i].data8[j];
			
			//write_iap(temp_data , segment_address + temp_add );
			write_iap( energy[i].data8[j], segment_address + temp_add );
		}//end of for(j)
	}//end of for(i)
	temp_data = write_iap( SAVE_OK , segment_address + 91);//test
	/////////////////////////////////////////////////////////
	EA = 1;
}//end of save_en_to_e2prom()


/************************************************************************************
               从FLASH中读取存放的电能值
*************************************************************************************/
/************************************************************************************
用于生产时判断掉电保存是否成功
上电时如果LED状态与掉电保存状态的对应该关系

           rec_led(D09)        trx_led(D08)      状态
              亮                    亮           整数与累加部分全部保存成功
              灭                    亮           整数部分保存成功
              灭                    灭           整数与累加部分全部保存不成功或未曾掉电
*************************************************************************************/
void read_en_from_flash()
{
	uchar idata i,j;
	uchar idata temp_data;
	uchar idata temp_add = 0;
	uint  idata segment_address;
	
	look_for_flag();
	
	EA = 0;
	///////////////////
	rec_led  = 0;//用于生产时判断掉电保存是否成功
	trx_led  = 0;
	//////////////////////////////////////////////////////////////////
	if( data_segment_flag == 0xff)
	{
		for( i = 0; i < sizeof( rwdata ); i++)
		{
			rwdata.serie_data8[i] = 0x00;   
		}
		
		for( i = 0; i < 9 ; i++ )
		{
			energy[i].data32 = 0;
		}
		/////////////////////////
		rec_led  = 1;//用于生产时判断掉电保存是否成功
		trx_led  = 1;
		////////////////////////04-8-19 13:20
		return;
	
	}
	
	segment_address = DATA_START + (uint)data_segment_flag * DATA_SEGMENT_LEN;
	
	if( read_iap( segment_address ) != SAVE_OK) 
	{
		for( i = 0; i < sizeof( rwdata ); i++)
		{
			rwdata.serie_data8[i] = 0x00;   
		}
		
		for( i = 0; i < 9 ; i++ )
		{
			energy[i].data32 = 0;
		}
		/////////////////////////
		rec_led  = 1;//用于生产时判断掉电保存是否成功
		trx_led  = 1;
		/////////////////////////
		return;
	}
	
	//the part of "kwh"
	for(i = 0; i < 3 ; i++)
	{
		for( j = 0; j < 4 ; j++)
		{
			temp_add++;
			
			temp_data = read_iap( segment_address + temp_add );
			
			rwdata.working.watt_hour[i].data8[j] = temp_data;
		}//end of for(j)
	}//end of for(i)
	
	for(i = 0; i < 3 ; i++)
	{
		for( j = 0; j < 4 ; j++)
		{
			temp_add++;
			
			temp_data = read_iap( segment_address + temp_add );
			
			rwdata.working.var_hour[i].data8[j] = temp_data;
		}//end of for(j)
	}//end of for(i)
	
	for(i = 0; i < 3 ; i++)
	{
		for( j = 0; j < 4 ; j++)
		{
			temp_add++;
			
			temp_data = read_iap( segment_address + temp_add );
			
			rwdata.working.va_hour[i].data8[j] = temp_data;
		}//end of for(j)
	}//end of for(i)
	
	////////////////////////////////////////////////////
	if( read_iap( segment_address + 90) != SAVE_OK) 
	{
		for( i = 0; i < sizeof( rwdata ); i++)
		{
			rwdata.serie_data8[i] = 0x00;   
		}
		for( i = 0; i < 9 ; i++ )
		{
			energy[i].data32 = 0;
		}
		/////////////////////////
		rec_led  = 1;//用于生产时判断掉电保存是否成功
		trx_led  = 1;
		/////////////////////////
		return;
	}//end of if( read_iap( segment_address + 90) != SAVE_OK) 
	
	//the part of "ws"
	for( i = 0; i < 9; i++)
	{
		for( j = 0; j < 4; j++)
		{
			temp_add++;
			
			temp_data = read_iap( segment_address + temp_add );
			
			energy[i].data8[j] = temp_data;
		}//end of for(j)
	}//end of for(i)
	
	if( read_iap( segment_address + 91) != SAVE_OK) 
	{
		for( i = 0; i < 9 ; i++ )
		{
			energy[i].data32 = 0;
		}
		/////////////////////////
		rec_led  = 1;//用于生产时判断掉电保存是否成功
		//trx_led  = 1;
		/////////////////////////
		return;
	}//end of if( read_iap( segment_address + 90) != SAVE_OK) 
	
	//EA = 1;
}//end of read_en_from_flash()


//////////////////////////////////////////////////////////////////////////////////

/********************************************************************************************
                  从E2PROM中读出已保存的校准参数
上电初始化时调用
*********************************************************************************************/

void clean_set_of7758()
{
	uchar i;
	
	for( i = 0; i < 3 ; i++)
	{
		rwdata.adjusting.write_data.voltage[i].data16  = 0;
	}//end of for(i)
	for( i = 0; i < 3 ; i++)
	{
		rwdata.adjusting.write_data.current[i].data16  = 0;
	}//end of for(i)
	
	for( i = 0; i < 3 ; i++)
	{	
		rwdata.adjusting.write_data.watt[i].data16     = 0;
	}//end of for(i)
	
	for( i = 0; i < 3 ; i++)
	{
		rwdata.adjusting.write_data.var[i].data16       = 0;
	}//end of for(i)
	
	for( i = 0; i < 3 ; i++)
	{
		rwdata.adjusting.write_data.va[i].data16       = 0;
	}//end of for(i)

	////////////////////
	write_to7758();
	////////////////////
		
}//end of read_set_from_e2prom()

/**********************************************************************************************
                     7758初始化函数

***********************************************************************************************/
void init_7758()
{
	uchar TempData,i;
	
	write_mask();//write interrupt mask to ade7758
	
	TempData = 0xff&read7753a(ADD_COMPMODE,8)|0x80; //
	
	write7753a(ADD_COMPMODE,((int)TempData<<8),8);//seting activate the no-load threshold
	
	if( bWorkModel )
	{
		clean_set_of7758();
		for(i = 0; i < 3; i++)
		{
			write7753a( ADD_WDIV + i, 0X00 , 8 );
		}
		
	}//end of if( bWorkModel )
	else
	{//正常工作模式
		read_set_from_e2prom();//read parameter from e2prom and write to ade7758
	}//else


}//end of init_7753()


/***************************************************************
检测7758是否异常,有则修复
****************************************************************/
uchar xdata back_buffer[sizeof(rwdata)];
void check_ade7758(void)
{
	uchar i;
	struct int_char temp,temp1;
	
	if( !b_adjust )//ADE7758已经校准标志
	return;
	
	temp.data8[0] = byte_read( SET_E2PROM_ADD + 1 );
	temp.data8[1] = byte_read( SET_E2PROM_ADD + 2 );
	
	temp1.data16 = read7753a( ADD_AVRMSGAIN ,12 ) & 0x0fff;
	
	if( temp.data16 != temp1.data16 )//检测A相校准参数是否正确
	{
		for( i = 0; i < sizeof( rwdata ); i++)
		{
			back_buffer[i] = rwdata.serie_data8[i];   //备份当前缓冲区的数据
		}
		
		read_set_from_e2prom();//该函数将改变当前缓冲区的数据
		
		for( i = 0; i < sizeof( rwdata ); i++)
		{
			rwdata.serie_data8[i] = back_buffer[i];   //恢复缓冲区的数据
		}
	}//end of if( temp.data16 != temp1.data16 )
}//end of check_ade7758(void)

⌨️ 快捷键说明

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