Other Parts Discussed in Thread: MSP430G2553,
Hello sir,
I have used DRV8305 and an MSP430G2553 controller to drive BLDC.
It runs almost perfectly but at some point of time BLDC motor internally make a sound for a second and that time waveform of Phase of U, V and W also get disturbed. This process is repeated but that is not at regular interval.
In my circuit, I have convert BLDC's hall sensor's 5V signal to 3.3V by using TXB0104PW. This is the image of that hall sensor circuit.
Below is code which I have taken from reference code for the one of TI reference design.
***********************************************************************************
// System Configuration
// Device Part Number : MSP430G2553
// compiler : Code Composer Studio 5.5.0.00077
// Oscillator Frequency : 16MHz, using internal DCO
// PWM generation : TIMER A1.2, 16MHz, OUTMOD[2:0]= 2,PWM for High Side FETs
// : TIMER A1.1, 16MHz, OUTMOD[2:0]= 6,PWM For Low side FEts
//
// Position Feedback : Hall sensors signals
// HA -> P2.0
// HB -> P2.7
// HC -> P2.6
//DRV8305
//SPI Communication : SDO -> P1.1
// : SDI -> P1.2
// : SCLK -> P3.4
// : SCS ->P3.5
//Fault Control : EN_GATE -> P3.6
// : FAULT ->P2.3
****************************************************************************************************/
#include <msp430.h>
#include <stdint.h>
#include "drv8305.h"
void Init_Clocks ();
void Init_IOs (void);
void Init_ADC (void);
void Init_Timer (void);
void Init_COMP_A (void);
void Hall_State_Change_FORWARD(void);
void Hall_State_Change_REVERSE(void);
void A_PWM(void);
void B_PWM(void);
void C_PWM(void);
void A_LOW(void);
void B_LOW(void);
void C_LOW(void);
void A_Z(void);
void B_Z(void);
void C_Z(void);
void Readfault(void);
#define PWM_PERIOD 400 //PWM Frequency (Hz) = 16MHz/((2*PWM_PERIOD)-1)
#define MAX_DUTYCYCLE 400 //relative to PWM_PERIOD
#define MIN_DUTYCYCLE 50 //relative to PWM_PERIOD
#define ACCEL_RATE 500 //Ramp up time to full scale duty cycle = (Full scale duty cycle) * ACCEL_RATE * PWM_PERIOD/PWM_Frequency
#define DEAD_TIME 1 // Dead time from MSP430 = DEAD_TIME* 0.0625 uS (for 16MHz clock)
#define Block_Rotor_Duration 30000 //Blocked_rotor shut off time (s) = Block_Rotor_Duration*30000/Timer clock frequency
#define WantedDutyCycle 390 //Wanted Duty Cycle
//unsigned int DC_BUS_CURRENT = 0;
//unsigned int DC_Bus_Voltage = 0;
unsigned int SPEED_REF = 0;
//unsigned int Temperature_feedback = 0;
//unsigned int start_count =0;
volatile unsigned int HALL_STATE = 0;
volatile unsigned int softstart_counter = 0;
//unsigned int WantedDutyCycle = 390;
volatile unsigned int CurrentDutyCycle =30;
volatile unsigned int DIRECTION=0 ;
//unsigned int FirstADC_flag =1;
//unsigned int ADC_selection_flag = 1;
//unsigned int ADC_selection_flag_1 =1;
unsigned int Block_Rotor_Counter = 0;
unsigned int Block_Rotor_Counter_1 =0;
unsigned int addr1, addr2, addr3, addr4;
/*******************************ADC channel selection*******************************************/
#define MEASURE_SPEED() { ADC10CTL0 = ADC10SHT_1 + ADC10IE + ADC10ON; \
ADC10CTL1 = INCH_3 + CONSEQ_0 + SHS_0; \
ADC10AE0 = BIT3; }
/*
#define MEASURE_TEMP() { ADC10CTL0 = ADC10SHT_1 + ADC10IE + ADC10ON; \
ADC10CTL1 = INCH_4 + CONSEQ_0 + SHS_0; \
ADC10AE0 = BIT4; }
#define MEASURE_VDC() { ADC10CTL0 = ADC10SHT_1 + ADC10IE + ADC10ON; \
ADC10CTL1 = INCH_5 + CONSEQ_0 + SHS_0; \
ADC10AE0 = BIT5; }
#define MEASURE_IDC() { ADC10CTL0 = ADC10SHT_1 + ADC10IE + ADC10ON; \
ADC10CTL1 = INCH_6 + CONSEQ_0 + SHS_0; \
ADC10AE0 = BIT6; }
*/
#define CONVERSION_ENABLE() { ADC10CTL0 |= ENC + ADC10SC; }
#define CONVERSION_DISABLE() { ADC10CTL0 &= ~ENC; \
ADC10CTL1 = 0; }
/*******************************Main************************************************************/
void main()
{
WDTCTL = WDTPW + WDTHOLD; // Stop watch-dog timer to prevent time out reset
Init_Clocks();
Init_IOs();
drv8305_init();
A_Z();
B_Z();
C_Z();
if((P2IN & BIT3) == 0)
{
ReadRegister(0x01);
ReadRegister(0x02);
ReadRegister(0x03);
ReadRegister(0x04);
//Readfault();
}
P3OUT |= BIT6;
Init_ADC();
// Init_COMP_A ();
Init_Timer();
WDTCTL = WDTPW + WDTHOLD; // Stop watch-dog timer to prevent time out reset
__delay_cycles(1000000);
HALL_STATE = (P2IN & BIT0) + ((P2IN & BIT6)>>4) + ((P2IN & BIT7)>>6);
//DIRECTION = (P3IN & BIT0);
DIRECTION=0;
P3OUT |= BIT1;
while(1)
{
if(DIRECTION == 1)
{
Hall_State_Change_FORWARD();
}
else
{
Hall_State_Change_REVERSE();
}
if(softstart_counter == ACCEL_RATE)
{
softstart_counter = 0;
if((P3IN & BIT0) == 1)
{
if ( CurrentDutyCycle < WantedDutyCycle )
{
CurrentDutyCycle++;
}
}
if((P3IN & BIT0)==0)
{
if (CurrentDutyCycle >= 10)
{
CurrentDutyCycle--;
}
}
}
}
}
/**************************Initializing ADC***********************************************/
void Init_ADC(void)
{
ADC10CTL0 = ADC10SHT_0 + ADC10ON + ADC10IE; // ADC10ON, interrupt enabled
ADC10CTL1 = INCH_3; //
}
/**************************Initializing GPIOs***********************************************/
void Init_IOs (void)
{
//Hall Sensor inputs
P2SEL &= ~(BIT0+BIT6+BIT7); //GPIO - Hall sensors
P2DIR &= ~(BIT0+BIT6+BIT7); //Inputs - Hall sensors
//PWM outputs
P2SEL |= (BIT1+BIT2+BIT4+BIT5); //GPIO-PWM
P2DIR |= (BIT1+BIT2+BIT4+BIT5); //Output-PWM
P3SEL |= (BIT2+BIT3); //GPIO-PWM
P3DIR |= (BIT2+BIT3); //OutputPWM
//P3SEL |= BIT7;
//P3DIR |= BIT7; //CAOUT
P3SEL &= ~(BIT7);
P3DIR |= BIT7; //LED1
//DRV8305
P2SEL &= ~(BIT3); //GPIO - FAULT
P2DIR &= ~(BIT3); //Inputs - FAULT
//P3SEL |= (BIT6); //GPIO-EN_GATE
P3DIR |= (BIT6); //Output - EN_GATE
// P3OUT |= BIT6;
//DRV8305-SPI communication
P1DIR |= BIT7; //GPIO-SDI
P1OUT &= ~BIT7; //Output-SDI
P1DIR &= ~BIT6; //SDO
P3DIR |= BIT4; //SCLK
P3OUT &= ~BIT4;
P3DIR |= BIT5; //nSCS
P3OUT |= BIT5;
//Indications
P3SEL &= ~ (BIT1); //GPIO-LED3
P3DIR |= (BIT1); //Output-LED3
//Direction Control
P3SEL &= ~(BIT0); //GPIO - DIR
P3DIR &= ~(BIT0); //Input - DIR
//Enable edge interrupt for Hall sensor ports
P2IES |= (BIT0)+(BIT6)+(BIT7); // EDGE DETECTION High = Falling Edge, Low = Rising Edge
P2IFG &= (~BIT0)+(~BIT6)+(~BIT7); // Pin 2.0, 2.6, and 2.7 IFG cleared
P2IE |= (BIT0)+(BIT6)+(BIT7) ; // Enable Interrupt on Input Pin 2.2, 2.3, and 2.4
__enable_interrupt();
}
/**************************Initializing Timer***********************************************/
void Init_Timer (void)
{
TA1CCR0 = PWM_PERIOD; // Load the Reference Count
TA1CCTL2 = OUTMOD_2; //High Side PWM
TA1CCR2 = 50;
TA1CCTL1 = OUTMOD_6; //Low Side PWM
TA1CCR1 = 50; //Initialized with zero
TA1CTL = TASSEL_2 + MC_3 + TACLR +TAIE ; //Up-Down Mode , SMCLK , Timer Clear; Timer Interrupt ON
//TA1CCTL0 = CCIE;
WDTCTL = WDT_MDLY_32; // approx 2ms interval
IE1 |= WDTIE; // enable WDT interrupt
_EINT(); // Enable interrupts
}
/**************************Initializing Clock***********************************************/
void Init_Clocks (void)
{
BCSCTL1 = CALBC1_16MHZ; // Set DCO ~ 16 Mhz
DCOCTL = CALDCO_16MHZ;
BCSCTL1 |= DIVA_1; // ACLK/(0:1,1:2,2:4,3:8)
BCSCTL3 |= LFXT1S_2; // LFXT1 = VLO
}
/**************************Port (hall sensor) Interrupt service routine***********************************************/
#pragma vector=PORT2_VECTOR
__interrupt void Port_2(void)
{
HALL_STATE = (P2IN & BIT0) + ((P2IN & BIT6)>>4) + ((P2IN & BIT7)>>6);
if(DIRECTION == 1)
{
Hall_State_Change_FORWARD();
}
else
{
Hall_State_Change_REVERSE();
}
P2IES ^= (BIT0)+(BIT6)+(BIT7); // change the hall interrupt to falling edge to detect both the edges
P2IFG &= (~BIT0)+(~BIT6)+(~BIT7); // Clear Interrupt Flag
}
/**************************Timer Interrupt vector***********************************************/
#pragma vector = TIMER1_A1_VECTOR
__interrupt void TIMER1_A1_ISR (void)
{
switch(__even_in_range(TA1IV,0x0A))
{
case TA1IV_NONE: break; // Vector 0: No interrupt
case TA1IV_TACCR1: break; // Vector 2: TACCR1 CCIFG
case TA1IV_TACCR2: break; // Vector 4: TACCR2 CCIFG
case TA1IV_6: break; // Vector 6: Reserved CCIFG
case TA1IV_8: break; // Vector 8: Reserved CCIFG
case TA1IV_TAIFG: // Vector 10: TAIFG
// TA1CCR2 = (CurrentDutyCycle);
// TA1CCR1 = CurrentDutyCycle;
TA1CCR2 = (CurrentDutyCycle -DEAD_TIME );
TA1CCR1 = CurrentDutyCycle;
if((P2IN & BIT3) == 0)
{
P3OUT &= ~(BIT6);
Readfault();
}
break;
default: break;
}
}
/**************************ADC INTERRUPT***********************************************/
#pragma vector=ADC10_VECTOR
__interrupt void ADC10_ISR (void)
{
SPEED_REF = (ADC10MEM>>1);
CONVERSION_DISABLE();
}
/**************************Commutation sequence Forward***********************************************/
void Hall_State_Change_FORWARD(void)
{
switch (HALL_STATE)
{
case 2:
A_PWM();
B_LOW();
C_Z();
break;
case 6:
A_PWM();
C_LOW();
B_Z();
break;
case 3:
C_PWM();
B_LOW();
A_Z();
break;
case 1:
C_PWM();
A_LOW();
B_Z();
break;
case 4:
B_PWM();
C_LOW();
A_Z();
break;
case 5:
B_PWM();
A_LOW();
C_Z();
break;
default:
A_Z();
B_Z();
C_Z();
break;
}
}
/**************************Commutation sequence Reverse***********************************************/
void Hall_State_Change_REVERSE(void)
{
switch (HALL_STATE)
{
case 2:
B_PWM();
A_LOW();
C_Z();
break;
case 6:
C_PWM();
A_LOW();
B_Z();
break;
case 3:
B_PWM();
C_LOW();
A_Z();
break;
case 1:
A_PWM();
C_LOW();
B_Z();
break;
case 4:
C_PWM();
B_LOW();
A_Z();
break;
case 5:
A_PWM();
B_LOW();
C_Z();
break;
default:
A_Z();
B_Z();
C_Z();
break;
}
}
/**************************Definition of PWM GPIOs***********************************************/
void A_PWM(void)
{
P3SEL |= BIT3;
P3SEL |= BIT2;
}
void B_PWM(void)
{
P2SEL |= BIT4;
P2SEL |= BIT2;
}
void C_PWM(void)
{
P2SEL |= BIT5;
P2SEL |= BIT1;
}
void A_LOW(void)
{
P3SEL &= ~BIT3;
P3OUT &= ~BIT3;
P3SEL &= ~BIT2;
P3OUT |= BIT2;
}
void B_LOW(void)
{
P2SEL &= ~BIT4;
P2OUT &= ~BIT4;
P2SEL &= ~BIT2;
P2OUT |= BIT2;
}
void C_LOW(void)
{
P2SEL &= ~BIT5;
P2OUT &= ~BIT5;
P2SEL &= ~BIT1;
P2OUT |= BIT1;
}
void A_Z(void)
{
P3SEL &= ~BIT3;
P3OUT &= ~BIT3;
P3SEL &= ~BIT2;
P3OUT &= ~BIT2;
}
void B_Z(void)
{
P2SEL &= ~BIT4;
P2OUT &= ~BIT4;
P2SEL &= ~BIT2;
P2OUT &= ~BIT2;
}
void C_Z(void)
{
P2SEL &= ~BIT5;
P2OUT &= ~BIT5;
P2SEL &= ~BIT1;
P2OUT &= ~BIT1;
}
void Readfault(void)
{
addr1 = ReadRegister(0x01);
addr2 = ReadRegister(0x02);
addr3 = ReadRegister(0x03);
addr4 = ReadRegister(0x04);
}
/**************************End****************************************************************/
So please help me for this. You can point out a error in code also.
Thank you.
Best Regards,
DINESH JINJALA



