Xin chào anh em trên diễn đàn , nhờ anh em hướng dẫn thành viên mới.
em đang sử dụng MPlab IDE v8.70 và HI-TECH PICC 9.82
để dịch chương trình ứng dụng kiểm tra thiết bị mô hình viết cho 16f883 từ trang
http://www.raconik.com/e-chex-multi-...vices-checker/
http://www.raconik.com/wp-content/up...2011/03/main.c
nhưng bị lỗi sau:
Executing: "C:\Program Files\HI-TECH Software\PICC\9.82\bin\picc.exe" --pass1 C:\main.c -q --chip=16F883 -P --runtime=default --opt=default -D__DEBUG=1 --rom=default --ram=default -g --asmlist "--errformat=Error [%n] %f; %l.%c %s" "--msgformat=Advisory[%n] %s" "--warnformat=Warning [%n] %f; %l.%c %s"
Warning [361] C:\main.c; 102.1 function declared implicit int
Error [192] C:\main.c; 199.1 undefined identifier "RBPU"
Error [192] C:\main.c; 432.1 undefined identifier "GODONE"
Warning [361] C:\main.c; 909.1 function declared implicit int
********** Build failed! **********
// man.c
//----------------------------------
// Project : E-CHEX
// PIC16F883 @ 8MHz internal
// Hi-tech PICC Pro 9.6PL5
// Last updated : November 17, 2009
//----------------------------------
#include <htc.h>
#include"delay.h"
// Configuration bit
// - Use internal RC for Oscillator
// - Watch-Dog Disabled
// - Power-up Timer Enabled
// - Internal reset MCLR pin use as I/O
// - Internal/External Switchover Disabled because using INTIO
// - Fail-Safe Clock Monitor Disabled because using INTIO
__CONFIG(INTIO&WDTDIS&PWRTEN&MCLRDIS&CP&DUNPROTECT &BORDIS&IESODIS&FCMDIS&LVPDIS&DEBUGDIS);
__CONFIG(BORV21);
#define Bemf_Rratio 12.02941176
#define BEC_Rratio 5.7
#define LiPo_Rratio 11.0
#define DeadBand 5
#define T0_Interval 48
#define NumberOfMode 5
#define MaxMode NumberOfMode - 1
#define MaxPole 14
#define Digit1 RA4 // pin 6
#define Digit2 RA6 // pin 10
#define Digit3 RA7 // pin 9
#define Switch RE3 // Pin 1
#define RX RB5 // Pin 26
#define ServoBit RB7 // Pin 28
#define DotMark 0xF7 // 11110111
// 7-Segment code commond anode
const char SegCode[16] = {0x28,0xF9,0x8A,0x98,0x59,0x1C,0x0C,0xF8,0x08,0x18 ,0xFF,0x1E,0xE8,0x8D,0x0E,0xCF};
volatile char DigitX[3]; // Buffer to store 7-segment code for each digit
static unsigned char DigitCnt,Debounce,FrameCnt,UpdateDisplayCnt;
volatile static char Mode;
static unsigned char StepInc;
static bit Update,DisplayModeFlag,ssw_flag,TimeSynFlag;
static unsigned char swState,SweepState,TimeSyn,Mode4State;
static bit ErrorPulseWidth,ShowPole,ServoEnabled,EnableReadSW ;
static char Pole;
unsigned int ppmWidth,NewVal;
unsigned int Cell[6];
static unsigned int Mode5Timer;
volatile static unsigned char ServoVal;
void Initial_IO(void);
void DisplayNumber(void);
void HTO7S(unsigned int Num);
void HTO7S2(unsigned int Num);
unsigned int ReadADC(unsigned char ch);
void TesterMode(void);
void MeasureMode(void);
unsigned int ReadPPM(void);
void ReadSwitch(void);
void CheckForUpdateDisplay(void);
void CenterMode(void);
void SweepMode(void);
void DisplayBatt(void);
void DisplayAllCell(unsigned int Volt);
void DisplayBECVolt(void);
void DisplayLine(void);
void KVMode(void);
unsigned int ReadVR(void);
//------------------------------------
// Main program
//------------------------------------
main(){
OSCCON = OSCCON | 0b01110000; // Enable Internal Clock at 8MHz
ServoEnabled = 0;
Initial_IO();
// check to see if ADC4 is Lipo inseted or not(Checking Cell 1 only)
if ((ReadADC(4) >= 20) && (ReadADC(10) >= 20)){
DisplayBatt();
}
DisplayBECVolt(); // Display BEC voltage
// Defualt mode is 0 after power on
// and display Mode Number on 7-segment 1Sec
DisplayModeFlag = 1;
DelayBigMs(1000);// Delay for showing Mode "1"
DisplayModeFlag = 0;
EnableReadSW = 1; // start to read Switch
//Mode = 4;
while(1){
switch (Mode){
case 0:{TesterMode();break;}
case 1:{CenterMode();break;}
case 2:{SweepMode();break;}
case 3:{MeasureMode();break;}
case 4:{KVMode();break;}
}
}
}
//-------------------------------------------------
// Interrupt Service Routine
// Timer 0 interrupt ever 6.667mS
//-------------------------------------------------
void interrupt isr(void){
if (T0IF){
T0IF=0;
TMR0 = T0_Interval;
DisplayNumber(); // Display every 6.667mS
CheckForUpdateDisplay(); // update display every about 33 mS
if (EnableReadSW){ ReadSwitch(); }
//----------------------------------
// Use in RX measurement mode only
//----------------------------------
TimeSyn ++;
if (TimeSyn>3){
TimeSyn = 0;
TimeSynFlag = 1;
}
if (ServoEnabled){
FrameCnt++;
if (FrameCnt>2){
FrameCnt=0;
//Set short timer1
PR2 = ServoVal - 2;
// Enable Timer 2.- every Timer 0 interrupt or 20ms = 1 short.
TMR2 = 0;
TMR2ON = 1;
TMR2IF = 0;
// Do not delete two this lines
NOP(); // optimize time interval for 0.7mS - 2.3mS
NOP(); // optimize time interval for 0.7mS - 2.3mS
ServoBit = 1;
ssw_flag = 1; // use in sweep mode to syn with servo
}
}
}
if (TMR2IF){
TMR2IF = 0;
TMR2ON = 0;
ServoBit=0;
}
}
//----------------------------------
// Initial I/O
//----------------------------------
void Initial_IO(void){
UpdateDisplayCnt = 0;
Pole = 7;
ShowPole = 0;
DigitCnt= 3;
EnableReadSW = 0;
Mode = 0;
swState = 0;
Update = 0;
ServoBit = 0;
// ANS0 for back emf
// ANS3 for Vdc/2
// ANS1,ANS2,ANS4-ANS7 for 6 cell lipo
ANSEL = 0b11111111;
// ANS9 for BEC
// ANS11 for VR 10K
ANSELH = 0b00011111;
RBPU = 0; // Pull-up on PortB
WPUB = 0b00100000; // RB5 pull-up for RX pin
//RE3 = 1;
//TRISE3 = 1; // Switch
/*
TRISA0 = 1; // input for ADC back emf
TRISA1 = 1; // Cell 6
TRISA2 = 1; // Cell 5
TRISA3 = 1; // Vdc/2
TRISA4 = 0; // Digit 1
TRISA5 = 1; // Cell 1
TRISA6 = 0; // Digit 2
TRISA7 = 0; // Digit 3
*/
TRISA = 0b00101111;
PORTC = 0xFF;
TRISC = 0x00; // PortC as output to control Digit row A to G, except RC7 use for switch
// RB7 servo, RB6 unused, RB5 RX, RB4 VR, RB3 BEC,
// RB2 Cell 3 AN8
// RB1 Cell 2 AN10
// RB0 Cell 4 AN12
//PORTB = 0b00110000;
RB6 = 0;
TRISB = 0b00111111; //
ADCON0 = 0b10000001; // AD conversion clock Fosc/32 = 4uS
ADCON1 = 0b10000000; // Right justified
T1CON = 0x00;
T2CON = 0b00100001;
TMR2IF = 0;
TMR2IE = 0;
//-----------------------------------
// Setup multi tasking
//-----------------------------------
T0CS = 0;
T0SE = 0;
PSA = 0;
PS2=1; PS1=0; PS0=1;
TMR0 = T0_Interval;
T0IE=1;
PEIE=1;
GIE=1;
}
//-----------------------------------
// Display Digit which is called by ISR
//-----------------------------------
void DisplayNumber(void){
if(DisplayModeFlag){
DigitX[0] = SegCode[Mode+1];// display number of mode(1-4)
DigitX[1] = SegCode[10]; // display blank
DigitX[2] = SegCode[10]; // display blank
}else if (ErrorPulseWidth){
DigitX[2] = SegCode[14]; // display "E"
DigitX[1] = SegCode[15]; // display "r"
DigitX[0] = SegCode[15]; // display "r"
}else if(ShowPole){
DigitX[2] = 0x42; // display "P."
DigitX[1] = SegCode[Pole/10]; // display "0"
DigitX[0] = SegCode[Pole%10]; // display "0"
}
DigitCnt++;
if (DigitCnt>2){
DigitCnt=0;
}
//Digit1=~Digit1;
//Digit2=~Digit2;
//Digit3=0;
//PORTC=~PORTC;
//-----------------------------
// Turn off all digits
//-----------------------------
Digit1=0; Digit2=0; Digit3=0;
PORTC = 0xFF;
//-----------------------------
switch(DigitCnt){
case 0:{PORTC = DigitX[0]; ; Digit1 = 1;break;}
case 1:{PORTC = DigitX[1]; ; Digit2 = 1;break;}
case 2:{PORTC = DigitX[2]; ; Digit3 = 1;break;}
}
}
//--------------------------------------
// Convet HEX 2 byte into 7-Segment code
// 3 digits x.xx
//--------------------------------------
void HTO7S(unsigned int Num){
unsigned int res;
DigitX[2]=(SegCode[Num/100] & DotMark);
res=Num%100;
DigitX[1]=SegCode[res/10];
res=res%10;
DigitX[0]=SegCode[res];
}
//--------------------------------------
// Convet HEX 2 byte into 7-Segment code
// 3 digits xx.x
//--------------------------------------
void HTO7S2(unsigned int Num){
unsigned int res;
DigitX[2]=SegCode[Num/100];
res=Num%100;
DigitX[1]=SegCode[res/10] & DotMark;
res=res%10;
DigitX[0]=SegCode[res];
}
//-------------------------------------
// Display Lipo and A123 Battery
//-------------------------------------
void DisplayBatt(void){
unsigned int V1,V2,V3,V4,V5,V6;
unsigned int TotalVolt;
unsigned char i,BattCnt;
BattCnt=0;
V1 = ReadADC(4);
if (V1>20){BattCnt++;}
V2 = ReadADC(10);
if (V2>20){BattCnt++;}
V3 = ReadADC(8);
if (V3>20){BattCnt++;}
V4 = ReadADC(12);
if (V4>20){BattCnt++;}
V5 = ReadADC(2);
if (V5>20){BattCnt++;}
V6 = ReadADC(1);
if (V6>20){BattCnt++;}
// display number of cell
DigitX[2] = SegCode[BattCnt]; // Display number of batt cell
DigitX[1] = 0xFF; // display "Blank"
DigitX[0] = 0x1E; // display "C"
DelayBigMs(1000); // delay 1 second
DisplayLine(); // display "---"
while(1){
V1 = ReadADC(4);
Cell[0] = V1 - 0;
V2 = ReadADC(10);
Cell[1] = V2 - V1;
V3 = ReadADC(8);
if (V3>V2){
Cell[2] = V3 - V2;
}else{
Cell[2] = 0;
}
V4 = ReadADC(12);
if(V4>V3){
Cell[3] = V4 - V3;
}else{
Cell[3] = 0;
}
V5 = ReadADC(3);
if (V5>V4){
Cell[4] = V5 - V4;
}else{
Cell[4] = 0;
}
V6 = ReadADC(1);
if (V6>V5){
Cell[5] = V6 - V5;
}else{
Cell[5] = 0;
}
for (i=0;i<BattCnt;i++){
DigitX[0] = SegCode[i+1]; // display number of cell(1-6)
DigitX[1] = 0x85; // display "o."
DigitX[2] = 0x68; // display "N"
DelayBigMs(500);
HTO7S((unsigned int)(Cell[i] * 0.003225806 * LiPo_Rratio * 100.0));
DelayBigMs(1000);
}
TotalVolt = Cell[0]+Cell[1]+Cell[2]+Cell[3]+Cell[4]+Cell[5];
DisplayAllCell(TotalVolt);
}
}
//------------------------------------
// Read ADC
// return 16th average 10 bit ADC value
//------------------------------------
unsigned int ReadADC(unsigned char ch){
unsigned char i;
unsigned int ADC;
ADCON0 = ((ADCON0 & 0b11000011) | (ch << 2));
NOP();NOP();NOP();NOP();NOP();
ADC = 0;
for (i=0;i<16;i++){
GODONE = 1;
while(GODONE) continue; // wait for conversion complete
ADC = ADC + ((ADRESH<<8) | ADRESL);
}
return (ADC>>4);
}
//--------------------------------------
// Read Pulse Width
// return : Pulse width 0.5mS - 2.5mS
// : 0 if pulse high or low > 2.5mS
//
// Actual Standard Pulse is 1mS - 2mS
//
//--------------------------------------
unsigned int ReadPPM(void){
TimeSyn = 0;
TimeSynFlag = 0;
while(!TimeSynFlag) continue;
TimeSynFlag = 0;
while(RX){
if (TimeSynFlag){
return 0;
}
}
//-----------------------------------------------
// Timer prescaler 1:1
// Fosc/4 = 0.5uS
// Timer 1 will count from
// EC78 to FFFF
// So time interval for counting is
// FFFFh - EC78h + 1 = 1388h
// or
// 65535 - 60536 + 1 = 5000
// 5000 * (prescaler 1:1) * 0.5uS = 2500uS = 2.5mS
//-------------------------------------------------
TMR1H = 0xEC;
TMR1L = 0x78;
TMR1ON = 1;
// wait high pulse
while(!RX){
if (TimeSynFlag){
return 0;
}
}
NOP();NOP();
while(RX){
if (TimeSynFlag){
return 0;
}
}
return ((((TMR1H<<8) | TMR1L) - 0xEC78) >> 1) ;
}
//------------------------------------
// Read Switch for changing mode
//------------------------------------
void ReadSwitch(void){
if (swState==0){
if (!Switch){
swState=1;
Debounce=0;
}
}else if(swState==1){
Debounce++;
if (Debounce>1){
if (!Switch){
DisplayModeFlag=1;
swState=2;
Debounce=0;
}else{
swState=0;
}
}
}else if(swState==2){
if (Switch){ // check to see switch released or not
swState=3; // Yes switch released goto next state
Debounce=0;
}else{
Debounce++;
if (Debounce>150){
Debounce=0;
if (Mode==4){
if (!Switch){
DisplayModeFlag=0;
ShowPole = 1;
swState=6;
}
}
}
}
}else if(swState==3){
Debounce++; // debounce when switch released
if (Debounce>1){
Debounce=0;
swState=4;
}
}else if(swState==4){ // checking switch pressed again or not in 1 Sec
Debounce++;
if (Debounce>150){
DisplayModeFlag=0;
Debounce=0;
swState=0;
}else if(!Switch){
swState=5;
Debounce=0;
}
}else if(swState==5){
Debounce++;
if (Debounce>1){
if (!Switch){
Mode++;
if (Mode>MaxMode){Mode=0;}
swState = 2;
}else{
swState=0;
}
}
}
//------------------------------------
// Use in Mode 4(KVM mode only)
//------------------------------------
else if(swState==6){
if (Switch){
Debounce = 0;
swState = 7;
}
}else if(swState==7){ // delay switch after switch released
Debounce++;
if (Debounce>2){
Mode5Timer = 0;
swState = 8;
}
//------------------------------------
}else if(swState==8){
Mode5Timer++;
if (Mode5Timer>300){
DisplayModeFlag=0;
ShowPole = 0;
swState = 0;
}else if (!Switch){
Debounce = 0;
swState = 9;
}
}else if(swState==9){
Debounce++;
if (Debounce>2){
Debounce = 0;
if (!Switch){
Pole++;
if (Pole>=(MaxPole+1)){
Pole = 1;
}
Mode5Timer = 0;
swState = 10;
}else{
swState = 8;
}
}
}else if(swState==10){
if (Switch){
Debounce = 0;
swState = 11;
}
}else if(swState==11){
Debounce++;
if (Debounce>2){
swState = 8;
}
}
}
//--------------------------------------
// Check before update display every 100mS
// Use on Tester Mode and Measure Mode only
//--------------------------------------
void CheckForUpdateDisplay(void){
UpdateDisplayCnt++;
if (UpdateDisplayCnt>15){
UpdateDisplayCnt = 0;
Update = 1;
}
}
//---------------------------------------
// Display All Cell of Batt
//---------------------------------------
void DisplayAllCell(unsigned int Volt){
DigitX[0] = 0x2F; // Display "L"
DigitX[1] = 0x2F; // display "L"
DigitX[2] = 0x48; // display "A"
DelayBigMs(500);
HTO7S2((unsigned int)(Volt * 0.003225806 * LiPo_Rratio * 10.0));
DelayBigMs(1000);
}
//---------------------------------------
// Display "---"
//---------------------------------------
void DisplayLine(void){
DigitX[0] = 0xDF; // Display "-"
DigitX[1] = 0xDF; // display "-"
DigitX[2] = 0xDF; // display "-"
DelayBigMs(1000);
}
//------------------------------------
// Read VR
//------------------------------------
unsigned int ReadVR(void){
return (ReadADC(11);
}
//--------------------------------------
// Display BEC after power on in test mode
//--------------------------------------
void DisplayBECVolt(void){
DigitX[0] = 0x2E; // Display "C"
DigitX[1] = 0x0E; // display "E"
DigitX[2] = 0x0D; // display "b"
DelayBigMs(1000);
HTO7S((unsigned int)(ReadADC(9) * 0.003225806 * BEC_Rratio * 100.0));
DelayBigMs(1000);
DisplayLine();
}
//------------------------------------
// Servo Tester Manual Mode
// Send pulse with 0.7mS - 2.3mS to servo
// Mode : 1
//------------------------------------
void TesterMode(void){
while(DisplayModeFlag) continue;
FrameCnt = 0;
ServoEnabled = 1;
TMR2IE = 1;
while(Mode==0){
// scale ADC value to Pulse width 700uS - 2300uS
// NewVal = ReadADC()/[(1023.0)/(2300.0-700.0))] + 700.0;
// ReadADC()
// -------------- + 700
// (1023 - 0)
// ----------
// (2300-700)
//NewVal = (unsigned int)(ReadVR()*1.56402737) + 700; // Vcc 3.3V
NewVal = (unsigned int)(ReadVR()*1.56555773) + 700; // Vcc 3.25V
if (NewVal>2300){ NewVal = 2300;}
ServoVal = NewVal/10;
//ServoVal =70;
if (Update){
Update = 0;
HTO7S(ServoVal); // display can show only 3 digits, so last digit cutted by divide by 10
}
}
ServoEnabled = 0;
}
//--------------------------------------
// Center Mode
// Mode : 2
//--------------------------------------
void CenterMode(void){
unsigned int VRPos;
while(DisplayModeFlag) continue;
FrameCnt = 0;
ServoEnabled = 1;
TMR2IE = 1;
ServoVal = 150;
while(Mode==1){
VRPos = ReadVR(); // VR return 0-1023 ,so half is 511.5
if (VRPos<=500){
ServoVal = 150;
}else if (VRPos>=521){
ServoVal = 152;
}
if (Update){
HTO7S(ServoVal); // display can show only 3 digits, so last digit cutted by divide by 10
Update = 0;
}
}
ServoEnabled = 0;
}
//-------------------------------------
// Sweep Mode
// Mode : 3
//-------------------------------------
void SweepMode(void){
unsigned char DelayStop;
while(DisplayModeFlag) continue;
FrameCnt = 0;
ServoEnabled = 1;
TMR2IE = 1;
//ServoVal = 70;
//DelayMs(100);
SweepState=0;
while(Mode==2){
if (ssw_flag){
ssw_flag=0;
StepInc = (unsigned char)((ReadVR()/((1023.0)/(9.0)))) + 1; // scale ADC value to 1-10
if(SweepState==0){
ServoVal = ServoVal + StepInc;
if (ServoVal>230){
ServoVal = 230;
SweepState=1;
DelayStop = 0;
}
}else if (SweepState==1){
DelayStop++;
if (DelayStop>15){
SweepState=2;
}
}else if (SweepState==2){
ServoVal = ServoVal - StepInc;
if (ServoVal<70){
ServoVal = 70;
SweepState=3;
DelayStop = 0;
}
}else if (SweepState==3){
DelayStop++;
if (DelayStop>15){
SweepState=0;
}
}
}
if (Update){
HTO7S(ServoVal); // display can show only 3 digits, so last digit cutted by divide by 10
Update = 0;
}
}
ServoEnabled = 0;
}
//------------------------------------
// Measure Mode
// Pulse width 0.7mS - 2.3mS is OK
// Display : Err if pulse are not in range
//
// Option (just option no need in this version)
// display "U-x" if pulse under 0.7mS
// display "O-x" if pulse over 2.3ms
// when x is error code
// Mode : 4
//------------------------------------
void MeasureMode(void){
ServoEnabled = 0;
T1CON = 0b11000000;
T1GSS = 1;
while(Mode==3){
ppmWidth = ReadPPM() ;
if (ppmWidth==0){
ErrorPulseWidth = 1; // Error caused by High or low too long(>2.5mS)
}else if ((ppmWidth>=700) && (ppmWidth<=2300)){
ErrorPulseWidth =0;
}
if (Update){
Update = 0;
HTO7S(ppmWidth/10); // display can show only 3 digits, so last digit cutted by divide by 10
}
}
ErrorPulseWidth =0;
T1CON = 0x00;
T1GSS = 0;
}
//--------------------------------------
// KV Measurement mode
// Use measuere Back EMF method
// Send pulse 1mS - 2mS to ESC
// Error < +/-5%
// Input : P Magnet Pole Pairs enter by user
// : Back EMF by measuring
// : Vdc by measuring
// Mode 5
//--------------------------------------
void KVMode(void){
unsigned int KVmotor, MecRPM, Bemf, Vdc;
unsigned int Ton, Toff, Ttotal, TCnt;
float FMecRPM, FBemf, FVdc;
while(DisplayModeFlag) continue;
ServoVal = 70;
FrameCnt = 0;
ServoEnabled = 1;
DelayBigMs(300);
Mode4State = 0;
// Comparator 1 on, Internal output, Non-invert, referrence form C1IN+ pin(Vdc/2)
// C12IN0- pin of C1 connects to C1VIN-
CM2CON0 = 0b00000000;
T1GSS = 0; // Timer1 gate source is SYNCC2OUT
C2SYNC = 1; // Output is synchronous to falling edge of Timer1 clock
// Timer 1
// Prescaler 1:8 TMR1L = 00-FF or 0 - 1mS (256 * 8 * 0.5uS ~ 1mS)
// So max frequency about 1kHz = 1/1mS
// Count Fosc/4 when gate high
//
T1CON = 0b11100001;
MecRPM = 0;
Bemf = 0;
KVmotor = 0;
Vdc = 0;
C2IE = 0; // disable comparator 2 intterupt
C2ON = 1; // Comparator 2 on
while(Mode==4){
//------------------------------------
// Checking for update display
//------------------------------------
if (Update){
Update = 0;
//HTO7S(MecRPM);
//HTO7S(Bemf);
HTO7S(KVmotor);
//HTO7S(Vdc);
}
if (Mode4State==0){
if (ReadVR()<10){
Mode4State=1;
DelayMs(100);
}
}else if (Mode4State==1){ // Measure pulse high
// scale 0 - 3.25V to 1mS - 2mS
NewVal = (unsigned int)((ReadVR() * 0.978473581) + 1000); // Vcc 3.25V
if (NewVal>2000){ NewVal = 2000;}
ServoVal = NewVal/10;
if (ServoVal>=199){
Mode4State=2;
Ton = 0;
Toff = 0;
TCnt = 0;
}
}else if (Mode4State==2){
C2POL = 0;
for (TCnt=0;TCnt<16;TCnt++){
while(!TimeSynFlag) continue;
TimeSynFlag = 0;
while(C2OUT){
if (TimeSynFlag){
break;
}
}
TMR1H = 0;
TMR1L = 0;
TMR1ON = 1;
// wait high pulse
while(!C2OUT){
if (TimeSynFlag){
break;
}
}
NOP();NOP();
while(C2OUT){
if (TimeSynFlag){
break;
}
}
Ton = Ton + ((TMR1H<<8) | TMR1L);
}
Ton = Ton>>4;
Mode4State=3;
}else if (Mode4State==3){ // Measure pulse low
C2POL = 1;
for (TCnt=0;TCnt<16;TCnt++){
while(!TimeSynFlag) continue;
TimeSynFlag = 0;
while(C2OUT){
if (TimeSynFlag){
break;
}
}
TMR1H = 0;
TMR1L = 0;
TMR1ON = 1;
// wait high pulse
while(!C2OUT){
if (TimeSynFlag){
break;
}
}
NOP();NOP();
while(C2OUT){
if (TimeSynFlag){
break;
}
}
Toff = Toff + ((TMR1H<<8) | TMR1L);
}
Mode4State=4;
}else if (Mode4State==4){ // Measure pulse low
C2POL = 0;
Bemf = 0;
for (TCnt=0;TCnt<16;TCnt++){
while(!TimeSynFlag) continue;
TimeSynFlag = 0;
while(C2OUT){
if (TimeSynFlag){
break;
}
}
NOP();NOP();NOP();NOP();NOP();NOP();NOP();NOP();
Bemf = Bemf + ReadADC(0);
}
Bemf = Bemf>>4;
//------------------------------------------------------------------------------
// FZero period is Ttotal = Ttotal * 2
//
// FZero = 1 = 500000
// -------------------- -------- Hz
// Ttotal * 4 * 0.5uS Ttotal
//
// When Ttotal = Ton + Toff
//
//
// 500000 60
// Mechanical rpm = -------- * ----------- (RPM)
// Ttotal Pole Pairs
//
//
// 30000000
// Mechanical rpm = --------------------
// Ttotal * Pole Pairs
//
// But Actual Ttotal of FZero obtained by
// Ttotal = 2 * Ttotal
// So new Mechanical rpm is
//
// 30000000 15000000
// Mechanical rpm = ------------------------ = ----------------------
// 2 * Ttotal * Pole Pairs Ttotal * Pole Pairs
//--------------------------------------------------------------------
//--------------------------------------------------------------------
// MecRPM
// KVmotor = ------
// Bemf
//
// 15000000
// = -------------------
// Ttotal * Pole Pairs
// --------------------------------------
// ReadADC(0) * 0.003225806 * 12.02941176
//
// 2
// Actual Bemf = --- * Measured Bemf
// 3
// = 0.6666666 * Measured Bemf(average measured voltage at coil terminal)
//----------------------------------------------------------------------
//Bemf = (unsigned int)(ReadADC(0) * 0.003225806 * BemfRratio * 100.0); // for display
//Vdc = (unsigned int)(((ReadADC(2) * 0.003225806 * 23.72727273)/ 2.0) * 100.0); // for display
//MecRPM = (unsigned int)(15000000.0/(Ttotal * Pole * 10.0)); // for display
Ttotal = Ton + (Toff>>4); // This is period for 360 eletric degree for FZero
FBemf = Bemf * 0.003225806 * Bemf_Rratio * (2.0/3.0);
//FVdc = (unsigned int)(((ReadADC(2) * 0.003225806 * 23.72727273)/ 2.0) + 0.3);
FMecRPM = 15000000.0/(Ttotal * Pole);
KVmotor = (unsigned int)(FMecRPM/FBemf)/10;
Mode4State=1;
}
}
C2ON = 0;
ServoEnabled = 0;
}