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

📄 att7027.c

📁 att7025是一个单相SOC的单心片电表方案
💻 C
字号:
 #include <ATT7027.H>
 #include <MAIN.H>
// #include <stddef.h>
 void Flash_Write_ATT7027(unsigned int addr,unsigned char *mt_data,unsigned char n);
 void Flash_Read_ATT7027(unsigned int addr,unsigned char *mt_data,unsigned char n);
 void WriteCALATT7027(unsigned char addr,unsigned char *mt_data,unsigned char n);
 void ReadATT7027(unsigned char addr,unsigned char *mt_data,unsigned char n);
 void ReadCALATT7027(unsigned char addr,unsigned char *mt_data,unsigned char n);
 void EMU_Parameter_change1();
/*******************************************************************
                 写FLASH数据
函数原型: void Flash_Write_ATT7027(unsigned int addr,unsigned char *mt_data,unsigned char n)
功能:     将要写的数据写到FLASH中
输入:    addr 地址,n个数,mt_data存放RAM的指针
输出:    
********************************************************************/
void Flash_Write_ATT7027(unsigned int addr,unsigned char *mt_data,unsigned char n)
{
	unsigned char i,ADDRL,ADDRH,TEMP;
	CFMCFG|=0x04;//	允许系统调用
 for(i=0;i<n;i++)
  { 
	ADDRL=addr;
	ADDRH=addr>>4;
	TEMP=*mt_data;
	BWPR=0xC3;//使能写PMOD[1:0]操作
	BWPR=0x9B;//开启所有受保护位的写使能	
 /* #pragma asm
	MOV	R6,ADDRH						//指定要擦除的页的高地址
	MOV	R7,ADDRL						//指定要擦除的页的低地址
	MOV	R3,1								//指定要擦除DATA FLASH
  LCALL	0FFD7H	
  MOV DPTRH0,ADDLH
  MOV DPTRL0,ADDRL
  MOV	A,TEMP;
  LCALL	0FFD9H  
  #pragma endasm */
  addr=addr+1;
  mt_data=mt_data+1;
  }	
}
/*******************************************************************
                 读FLASH数据
函数原型:void Flash_Read_ATT7027(unsigned int addr,unsigned char *mt_data,unsigned char n)
功能:     读FLASH数据放到mt_data指针指向要存放的地址中
输入:    addr子地址,n个数,*mt_data要存放的指针
输出: 
********************************************************************/
void Flash_Read_ATT7027(unsigned int addr,unsigned char *mt_data,unsigned char n)
{
 unsigned char i;
 for(i=0;i<n;i++)
  { 
  *mt_data=CBYTE[addr];
  addr=addr+1;
  mt_data=mt_data+1;
  }	
}



/****************************************************************************
                 写数据到校表寄存器中
函数原型:void WriteCALATT7027(unsigned char addr,unsigned char *mt_data,unsigned char n)
功能:     数据放到mt_data指针指向要存放的地址中
输入:    addr子地址,n个数,*mt_data要存放的指针
输出	comm:the val which written to the registers.
writes Calibration registers at att7027	addr:the address of the first register.
******************************************************************************/
void WriteCALATT7027(unsigned char addr,unsigned char *mt_data,unsigned char n)
{
	unsigned char i,delay;
	EPADR=0xA6;//ECR writes Calibration registers寄存器写保护使能
	for(i=0;i<n;i++)
	{ 
	ECADR=addr; //write address
		delay=10;
	while(delay>0) delay--;			// wait 4.8us
	ECDATH=*(mt_data+2*i);//写入数据的高8位如果单字节数据可以忽略此操作
	ECDATL=*(mt_data+1+2*i);//写入数据的低8位
	addr=addr+1;		//下一个校表参数
	}   
EPADR=0xA9;	//ECR writes Calibration registers寄存器写保护禁止  
}
/***********************************************************************
                 读电表寄存器数据
函数原型:void ReadATT7027(unsigned int addr,unsigned char *mt_data,unsigned char n)
功能:     读电表寄存器数据放到mt_data指针指向要存放的地址中
输入:    addr子地址,n个数,*mt_data要存放的指针
输出: 	This subroutine functions as reading n*bits registers from att7027.
	Considering the compatibilities, reading the 24bits register as 
		3*8bits, and reads 8bits once.
***********************************************************************/

void ReadATT7027(unsigned char addr,unsigned char *mt_data,unsigned char n)//*mt_data=xxxxxx00 n=3
{
  unsigned char delay,i=0;
	for(i=0;i<n;i++)
	{ 	
	EPADR=addr;  //write address
	delay=10;
	while(delay>0) delay--;			// wait 4.8us
    *(mt_data+3*i)=0;
	*(mt_data+1+3*i)=EPDATH;//读数据的高位如果寄存器为2字节,EPDATH 为符号扩展位
	*(mt_data+2+3*i)=EPDATM;//读数据的中间8位
	*(mt_data+3+3*i)=EPDATL;//读数据的低8位
	addr=addr+1;		
	} 	
}
/****************************************************************************
                 读电表校验寄存器数据
函数原型:void ReadCALATT7027(unsigned int addr,unsigned char *mt_data,unsigned char n)
功能:     读电表校验寄存器数据放到mt_data指针指向要存放的地址中
输入:    addr子地址,n个数,*mt_data要存放的指针
	Read Calibration registers at att7027
	addr:the address of the first register.
	comm:the val which written to the registers.
******************************************************************************/
void ReadCALATT7027(unsigned char addr,unsigned char *mt_data,unsigned char n)//*mt_data=xxxxxx00 n=3
{
  unsigned char delay,i=0;
	for(i=0;i<n;i++)
	{ 	
	EPADR=addr;  //write address
	delay=10;
	while(delay>0) delay--;			// wait 4.8us
	*(mt_data+2*i)=ECDATH;//读数据的高8位如果单字节数据可以忽略此操作
	*(mt_data+1+2*i)=ECDATL;//读数据的低8位
	addr=addr+1;		//下一个校表参数
	} 	
}
/****************************************************************************
                 电表寄存器经过转变为实际数据
函数原型:void EMU_Parameter_change1()
功能:     电表寄存器经过转变为实际数据
输入:    
	Read Calibration registers at att7027
	addr:the address of the first register.
	comm:the val which written to the registers.
******************************************************************************/
void EMU_Parameter_change1()
{
  unsigned char i;
  unsigned long *PA1,*PA2;
  unsigned long tempA;
  ReadATT7027(0,(unsigned char*)Emu_Parameter.Current_Waveform_Spl_I1,sizeof(Emu_Parameter));//SIZE_OF(Emu_Parameter,Current_Waveform_Spl_I1)Emu_Parameter_change
    PA1=&(Emu_Parameter.Current_Waveform_Spl_I1);
   // *temp1=  SIZE_OF(EEPROM_DATA,Apparent_Power_Gain_GS2);
    //*temp1=  sizeof(Emu_Parameter.Current_Waveform_Spl_I1);
	//*temp1=  SIZE_OF(Emu_Parameter.Current_Waveform_Spl_I1);
	PA2=&(Emu_Parameter_change.Current_Waveform_Spl_I1);
	for(i=0;i<3;i++)// Current_Waveform_Spl_I1 Current_Waveform_Spl_I2 Voltage Waveform_Spl_U;	
	{
     if((*PA1)>=0x8000)  //2^15
	 *PA2=(0x10000-(*PA1)); //2^16     
     else *PA2=*PA1;
       PA1=PA1+1;
	   PA2=PA2+1;
		}
    for(i=0;i<3;i++)// Active_Power_Waveform_Spl_P 	
	{               //Reactive_Power_Waveform_Spl_Q Apparent Power Waveform_Spl_S ;
	  if((*PA1)>=0x800000)  //2^23
       *PA2=(0x1000000-(*PA1)); //2^24
      else *PA2=*PA1;
       PA1=PA1+1;
	   PA2=PA2+1;
	}	
	for(i=0;i<3;i++)//Current_Rms_I1 Current_Rms_I2  Current_Rms_U;	
	{
	tempA=(*(unsigned long*)&Emu_Parameter_change.EMU_Krms_Rms[i])>>16;
	*PA2=((*PA1)*tempA);//Kp=5/234880*001000=2.1287466×10^(-4)
			//	PA=Emu_Parameter_change.EMU_Krms_Rms[i];
	PA1=PA1+1;
	PA2=PA2+1;
	}
	*PA2=(5529600/6/(*PA1))<<8;	//femu =5529600Hz	f=femu/6/UFREQ Current_Freq_U; 
	PA1=PA1+1;
	PA2=PA2+1;
	for(i=0;i<3;i++)// Active_Power_P Reactive_Power_Q  Apparent_Power_S; 
	{
	if((*PA1)>=0x800000)  //2^23
       *PA1=0x1000000-(*PA1); //2^24	 
    tempA=*(unsigned long*)&Emu_Parameter_change.EMU_Krms_Kpqs[i]>>16;//Kpqs=1000/51673=0.01935
    //*temp2=(*temp1)*(*tempA);//P=Kpqs*Preg=0.01935*(-47820)= -925.3 w
	*PA2=((*PA1)*(tempA));		
    PA1=PA1+1;
	PA2=PA2+1;
		}
	for(i=0;i<3;i++)//  Active_Energy_P Reactive_Energy  Apparent_Energy_S;
	{
	tempA=*(unsigned long*)meter_para.MeterConstantReal;
    *PA2=((*PA1)/(tempA));
    PA1=PA1+1;
	PA2=PA2+1;
		}					
} 

/****************************************************************************
                 电表通过RS485communicate进行校表
函数原型:void Calibration_meter(void)
功能:     读RS485communicate数据放到mt_data指针指向电表校验寄存器要存放的地址中
输入:    
	Read Calibration registers at att7027
	addr:the address of the first register.
	comm:the val which written to the registers.
******************************************************************************/
void Calibration_meter(void)
{
  //unsigned char data_id;
  //unsigned char cali_data[3];	    
  /*  data_id=rxdatabuffer[10];
	 //较表写命令 
	    if((data_id>=0x41)&&(data_id<=0x48)||(data_id>=0x4A)&&(data_id<=0x4F))
	    {
         cali_data[0]=rxdatabuffer[11];
	       cali_data[1]=rxdatabuffer[12];	       
	       // cali_data  Data_ID write ram and ATT7027 
	       WriteCALATT7027(data_id,&cali_data[0],2)
	       Write_EEPROM(2,&cali_data[0],(0x40+(data_id-1)*2));              
	    }
	    //较表读电压电流 
	    else if((data_id==0x0F)||(data_id==0x10))
	    {
	         rxdatabuffer[9]=6;	
	         rxdatabuffer[8]+=0x40;
	        
	       //返回数据在10-15  
	       if(data_id==0x0F)
	       {
	       	  rxdatabuffer[10]=*((unsigned char *)&Emu_Parameter.Current_Rms_I1+2);
	       	  rxdatabuffer[11]=*((unsigned char *)&Emu_Parameter.Current_Rms_I1+3);
	       }
	       else if(data_id==0x10)
	       {
	       	  rxdatabuffer[10]=*((unsigned char *)&Emu_Parameter.Current_Rms_I2+2);
	       	  rxdatabuffer[11]=*((unsigned char *)&Emu_Parameter.Current_Rms_I2+3);
	       }
	       else 
	       {
	       	  rxdatabuffer[10]=*((unsigned char *)&Emu_Parameter.Current_Rms_U+2);
	       	  rxdatabuffer[11]=*((unsigned char *)&Emu_Parameter.Current_Rms_U+3);
	       }	       
	    }
	    //错误命令回错误应答 
	    else
	    {
	       rxdatabuffer[9]=1;	
	       rxdatabuffer[8]+=0x40;
        }
*/
}

⌨️ 快捷键说明

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