RTL00MP3/RTL00_SDKV35a/example_sources/spi_pl7223/src/main.c

299 lines
8.6 KiB
C
Raw Normal View History

2016-12-14 01:21:37 +00:00
/*
* Routines to access hardware
*
* Copyright (c) 2015 Realtek Semiconductor Corp.
*
* This module is a confidential and proprietary property of RealTek and
* possession or use of this module requires written permission of RealTek.
*/
#include <stdio.h>
#include <math.h>
#include "device.h"
#include "main.h"
#include "spi_api.h"
#include "gpio_api.h"
// SPI0
#define SPI0_MOSI PC_2
#define SPI0_MISO PC_3
#define SPI0_SCLK PC_1
#define SPI0_CS PC_0
#define GPIO_RESET PB_4
#define GPIO_CS PB_5
//--------------------------------------------------------------------------------------------
#define READ_PL7223 0x4000
#define WRITE_PL7223 0x8000
#define DSPSTATUS_PL7223 0xF000
#define DUM_PL7223 0x00 //Dummy Data
unsigned char SPDAT; // simulate example code
unsigned char DSP_STATUS=0;
unsigned char Read_Data_PL7223[146]; // Read_Data; 256Bytes=1Page
unsigned char Write_Data_PL7223[146]; // Write_Data; 256Bytes=1Page
unsigned char Cmd_RD=0;
long EE_Temp = 0;
float VA_rms=0;
float IA_rms=0;
float PA=0;
float SA=0;
float QA=0;
float PF_A=0;
float Theta_A=0;
float Frequency=0;
int Sample_cnt0=0;
int ZCC_cnt=0;
int ZCC_Start=0;
int ZCC_Stop=0;
void Initial_SPI_PL7223(void);
void SPI_PL7223_SEND(unsigned char);
void SPI__PL7223_Read_Status(void);
void SPI_PL7223_DELY(int);
void SPI_PL7223_Reset(void);
void SPI_PL7223_Read(unsigned char*, unsigned int, unsigned int);
void SPI_PL7223_Write(unsigned char*, unsigned int, unsigned int);
void SPI_PL7223_Masurement(void);
void SPI_PL7223_RelayControl(int);
static spi_t spi0_master;
static gpio_t gpio_reset;
static gpio_t gpio_cs;
/**
* @brief Main program.
* @param None
* @retval None
*/
void main(void)
{
gpio_init(&gpio_reset, GPIO_RESET);
gpio_mode(&gpio_reset, PullUp);
gpio_dir(&gpio_reset, PIN_OUTPUT);
gpio_init(&gpio_cs, GPIO_CS);
gpio_mode(&gpio_cs, PullUp);
gpio_dir(&gpio_cs, PIN_OUTPUT);
spi_init(&spi0_master, SPI0_MOSI, SPI0_MISO, SPI0_SCLK, SPI0_CS);
spi_format(&spi0_master, 8, 3, 0);
spi_frequency(&spi0_master, 800000);
do
{
SPI_PL7223_Reset();
SPI_PL7223_Read(&Read_Data_PL7223[0],0x3860,1);//DSP version :20130322 ver02, 0x3860=0x04
//DSP version :20141009 ver01, 0x3860=0x03
}while( ((Read_Data_PL7223[0]) != 0x04) && ((Read_Data_PL7223[0]) != 0x03) );
SPI_PL7223_DELY(120000);
SPI_PL7223_RelayControl(0); // OFF
SPI_PL7223_DELY(120000);
do{
// As below is read DSP buffer process every time (144 byte)
SPI__PL7223_Read_Status();
SPI_PL7223_Read(&Read_Data_PL7223[0],0x3000,144); // 0x3000~0x308F //144 byte
SPI_PL7223_Read(&Read_Data_PL7223[144],0x3809,2); // Sample_cnt0
SPI_PL7223_Masurement();
SPI_PL7223_DELY(600000);
SPI_PL7223_RelayControl(1); // ON
SPI_PL7223_DELY(120000);
SPI__PL7223_Read_Status();
SPI_PL7223_Read(&Read_Data_PL7223[0],0x3000,144); // 0x3000~0x308F //144 byte
SPI_PL7223_Read(&Read_Data_PL7223[144],0x3809,2); // Sample_cnt0
SPI_PL7223_Masurement();
SPI_PL7223_DELY(600000);
SPI_PL7223_RelayControl(0); // OFF
SPI_PL7223_DELY(120000);
}while(1);
}
//--------------------------------------------------------------------------------------------//
void SPI_PL7223_RelayControl(int sw)
{
#define RELAY_MASK (1<<5)
SPI_PL7223_Read(&Read_Data_PL7223[0],0x380F,1);
if(!sw)
Read_Data_PL7223[0] &= (~RELAY_MASK);
else
Read_Data_PL7223[0] |= RELAY_MASK;
SPI_PL7223_Write(&Read_Data_PL7223[0],0x380F,1);
}
//--------------------------------------------------------------------------------------------//
void SPI_PL7223_Reset(void)
{
gpio_write(&gpio_cs, 0);
SPI_PL7223_DELY(500); //need delay 10ms
gpio_write(&gpio_reset, 1);
SPI_PL7223_DELY(500); //need delay 10ms
gpio_write(&gpio_reset, 0);
SPI_PL7223_DELY(500); //need delay 10ms
gpio_write(&gpio_reset, 1);
SPI_PL7223_DELY(500); //need delay 10ms
gpio_write(&gpio_cs, 1);
SPI_PL7223_DELY(300);
}
//--------------------------------------------------------------------------------------------//
void SPI__PL7223_Read_Status(void)
{
gpio_write(&gpio_cs, 0);
SPI_PL7223_SEND((unsigned char)(DSPSTATUS_PL7223 >> 8)& 0xFF); // RDSR command
SPI_PL7223_SEND((unsigned char)(DSPSTATUS_PL7223& 0x00FF)); // RDSR command
//check DSP flag state (byte)
do
{
SPI_PL7223_SEND(DUM_PL7223);
DSP_STATUS=SPDAT;
}while((DSP_STATUS & 0x80) == 0x00); // Bit7=1 is Ready
gpio_write(&gpio_cs, 1);
}
//--------------------------------------------------------------------------------------------//
void SPI_PL7223_Write(unsigned char* buf, unsigned int addr, unsigned int len)
{
unsigned int i;
gpio_write(&gpio_cs, 0);
addr |= WRITE_PL7223; // Write command
SPI_PL7223_SEND((unsigned char)(addr >> 8)& 0xFF); // Write middle byte address
SPI_PL7223_SEND((unsigned char)(addr & 0xFF));// Write low byte address
for (i = 0; i < len ; i++){
SPI_PL7223_SEND(buf[i]);
}
gpio_write(&gpio_cs, 1);
SPI_PL7223_DELY(3); // for CS:Hi to Low need 100nsec, Delay-Time 27usec
}
//--------------------------------------------------------------------------------------------//
void SPI_PL7223_Read(unsigned char* buf, unsigned int addr, unsigned int len)
{
static unsigned int i;
gpio_write(&gpio_cs, 0);
addr |= READ_PL7223; // Read command
SPI_PL7223_SEND((unsigned char)(addr >> 8)& 0xFF); // Write middle byte address
SPI_PL7223_SEND((unsigned char)(addr & 0x00FF)); // Write low byte address
for(i=0;i<len;i++){ // Read 256 Bytes/Page to Flash Memory
SPI_PL7223_SEND(DUM_PL7223); // Send Dummy Data to Read righ Data
buf[i] = SPDAT; // Read SPIDAT and clear TX complete flag
}
gpio_write(&gpio_cs, 1);
}
//--------------------------------------------------------------------------------------------//
void SPI_PL7223_Read_Status(void)
{
gpio_write(&gpio_cs, 0);
SPI_PL7223_SEND((unsigned char)(DSPSTATUS_PL7223 >> 8)& 0xFF); // RDSR command
SPI_PL7223_SEND((unsigned char)(DSPSTATUS_PL7223& 0x00FF)); // RDSR command
do
{
SPI_PL7223_SEND(DUM_PL7223);
DSP_STATUS=SPDAT;
}while((DSP_STATUS & 0x80) == 0x00); // Bit7=1 is Ready
gpio_write(&gpio_cs, 1);
}
//--------------------------------------------------------------------------------------------//
void SPI_PL7223_Masurement(void)
{
//Vrms address : 0x3002~0x3003
// VA_rms = (Read_Data_PL7223[3]*256+Read_Data_PL7223[2])/64;
EE_Temp = Read_Data_PL7223[3];
EE_Temp = EE_Temp << 8;
EE_Temp += Read_Data_PL7223[2];
VA_rms = (float)EE_Temp/64.00;
//Irms address : 0x3008~0x3009
// IA_rms = Read_Data_PL7223[3]+Read_Data_PL7223[2]/256;
EE_Temp = Read_Data_PL7223[8];
IA_rms = (float)EE_Temp/256.00;
EE_Temp = Read_Data_PL7223[9];
IA_rms = IA_rms + (float)EE_Temp;
//Active address : 0x3078~0x307D
// PA = Read_Data_PL7223[124]*256+Read_Data_PL7223[123];
EE_Temp = Read_Data_PL7223[124];
EE_Temp = EE_Temp << 8;
EE_Temp += Read_Data_PL7223[123];
PA = (float)EE_Temp;
//PF Calculate
// SA = VA_rms*IA_rms;
SA = VA_rms*IA_rms;
// PF_A = PA/SA
PF_A = SA==0? 0: PA/SA;
Theta_A = acos(PF_A);
QA = SA * sin(Theta_A);
if(IA_rms==0)
Theta_A = 0;
else
Theta_A = Theta_A * (180.00/(3.141592653589));
/** Frequency = [Sample_cnt0/(ZCC_STOP-ZCC_START)]*[(ZCC_CNT-1)/2] */
Sample_cnt0 = Read_Data_PL7223[145]; // Sample_cnt01
Sample_cnt0 = Sample_cnt0 <<8;
Sample_cnt0 += Read_Data_PL7223[144]; // Sample_cnt00
ZCC_cnt = Read_Data_PL7223[91]; // ZCC_cnt1
ZCC_cnt = ZCC_cnt <<8;
ZCC_cnt += Read_Data_PL7223[90]; // ZCC_cnt0
ZCC_Stop = Read_Data_PL7223[97]; // ZCC_STOP1
ZCC_Stop = ZCC_Stop <<8;
ZCC_Stop += Read_Data_PL7223[96]; // ZCC_STOP0
ZCC_Start = Read_Data_PL7223[103]; // ZCC_START1
ZCC_Start = ZCC_Start <<8;
ZCC_Start += Read_Data_PL7223[102]; // ZCC_START0
Frequency = (float)((float)Sample_cnt0 / (ZCC_Stop - ZCC_Start)) * (((float)ZCC_cnt - 1.0) / 2);
#define UART_Display(name) printf(#name" %d.%d\n\r", (int)(name*1000)/1000, (int)(name*1000)%1000)
UART_Display(VA_rms);
UART_Display(IA_rms);
UART_Display(Frequency);
UART_Display(PA);
UART_Display(QA);
UART_Display(SA);
UART_Display(PF_A);
UART_Display(Theta_A);
}
//--------------------------------------------------------------------------------------------//
void SPI_PL7223_DELY(int dely_cnt) // MCUCLK 4MHz, Delay-Time 9usec/clock
{
HalDelayUs(dely_cnt*20);
}
//--------------------------------------------------------------------------------------------//
void SPI_PL7223_SEND(unsigned char spicmd)
{
SPDAT = (char)spi_master_write(&spi0_master, (int)spicmd);
}
//--------------------------------------------------------------------------------------------//