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

📄 pmsm.h

📁 ATtiny261 461 861 这份资料介绍了执行Attiny261 461 861微控制器系列正弦波驱动三相无刷直流电动机霍尔传感器。
💻 H
字号:
/* This file has been prepared for Doxygen automatic documentation generation.*/
/*! \file *********************************************************************
 *
 * \brief
 *      Motor control header file.
 *
 *      This file contains all defines, typedefs and prototypes related to
 *      the motor control.
 *
 * \par Application note:
 *      AVR447: Sinusoidal driving of three-phase permanent motor using
 *      ATtiny261/461/861.
 *
 * \par Documentation
 *      For comprehensive code documentation, supported compilers, compiler
 *      settings and supported devices see readme.html
 *
 * \author
 *      Atmel Corporation: http://www.atmel.com \n
 *      Support email: avr@atmel.com
 *
 * $Name: RELEASE_1_0 $
 * $Revision: 1.5 $
 * $RCSfile: PMSM.h,v $
 * $Date: 2006/05/18 09:15:31 $  \n
 ******************************************************************************/
#ifndef _PMSM_H_
#define _PMSM_H_


#include "stdint.h"


/*! \brief Collection of all motor control flags.
 *
 *  This struct contains all motor control flags used in this implementation.
 */
typedef struct PMSMflags
{
  uint8_t motorStopped : 1;     //! Is motor stopped?
  uint8_t motorSynchronized: 1; //! Is motor synchronized? Does not have any meaning when motorStopped is TRUE.
  uint8_t actualDirection : 2;  //! The actual direction of rotation.
  uint8_t desiredDirection : 1; //! The desired direction of rotation.
  uint8_t driveWaveform : 2;    //! The current waveform that should be produced.
} PMSMflags_t;


//! FALSE constant value.
#define FALSE   0

//! TRUE constant value, defined to be compatible with comparisons.
#define TRUE    (!FALSE)


//! CPU clock frequency.
#define CPU_FREQUENCY               16000000UL

//! Dead time (Timer/counter1 clock cycles).
#define DEAD_TIME     10


#ifndef PWM1X
/*! \brief Bit position of PWM1X flag in TCCR1B register.
 *
 *  Bit position of PWM1X flag in TCCR1B register. Included in this file
 *  becuase it was not defined in the compilers header files.
 */
#define PWM1X   7
#endif


//! Pin connected to UL.
#define UL            PB0

//! Pin connected to UH.
#define UH            PB1

//! Pin connected to VL.
#define VL            PB2

//! Pin connected to VH.
#define VH            PB3

//! Pin connected to WL.
#define WL            PB4

//! Pin connected to WH.
#define WH            PB5

//! Mask of all pins used for motor control PWM outputs.
#define PWM_PIN_MASK_PORTB ((1 << UL) | (1 << UH) | (1 << VL) | (1 << VH) | (1 << WL) | (1 << WH))


//! Pin where hall sensor 1 is connected.
#define H1_PIN        PA0

//! Pin where hall sensor 2 is connected.
#define H2_PIN        PA1

//! Pin where hall sensor 3 is connected.
#define H3_PIN        PA2

//! Hall sensor pull-up enable. Set to TRUE to enable, FALSE to disable.
#define HALL_PULL_UP_ENABLE   FALSE
//#define HALL_PULL_UP_ENABLE   TRUE


//! Pin where direction input signal is connected.
#define DIRECTION_PIN PA3


//Output compare override enable bits
#define UL_OCOE       OC1OE0
#define UH_OCOE       OC1OE1
#define VL_OCOE       OC1OE2
#define VH_OCOE       OC1OE3
#define WL_OCOE       OC1OE4
#define WH_OCOE       OC1OE5


//! Output compare register for phase U.
#define COMPARE_REGISTER_PHASE_U           OCR1A

//! Output compare register for phase V.
#define COMPARE_REGISTER_PHASE_V           OCR1B

//! Output compare register for phase W.
#define COMPARE_REGISTER_PHASE_W           OCR1D


/*! \brief Selects inversion of PWM outputs.
 *
 *  Setting this flag to "1" causes the PWM outputs from Timer/Counter1 to
 *  be inverted. Inversion happens after dead time insertion.
 */
#define PWM_INVERT_OUTPUT       0
//#define PWM_INVERT_OUTPUT       1


//! Forward direction flag value.
#define DIRECTION_FORWARD       0

//! Reverse direction flag value.
#define DIRECTION_REVERSE       1

//! Unknown direction flag value.
#define DIRECTION_UNKNOWN       3


/*! \brief The number of elements in the sine modulation table per phase.
 *
 *  This is the number of elements in the sine modulation table used to
 *  represent the waveform for one phase. Note that this is not the same
 *  as the number of elements in the sineTable stored in flash.
 */
#define SINE_TABLE_LENGTH   192U

//! SINE_TABLE_SIZE value for large (3 * 192 elements) sine table.
#define SINE_TABLE_SIZE_LARGE   0

//! SINE_TABLE_SIZE value for small (64 elements) sine table.
#define SINE_TABLE_SIZE_SMALL   1

/*! Sine table size. Select what sine table size should be used.
 *
 *  \todo Select sine table size.
 */
#define SINE_TABLE_SIZE       SINE_TABLE_SIZE_LARGE
//#define SINE_TABLE_SIZE       SINE_TABLE_SIZE_SMALL


//! The number of elements in the sine modulation table for each phase per commutation sector.
#define TABLE_ELEMENTS_PER_COMMUTATION_SECTOR   (SINE_TABLE_LENGTH / 6)


//! Top value of Timer/Counter1.
#define PWM_TOP_VALUE       0x03ff


/*! The number of commutation 'ticks' that must pass without any hall changes
 *  before the motor is considered to be stopped.
 *
 *  \todo Adjust the motor stopped limit.
 */
#define COMMUTATION_TICKS_STOPPED     6000


/*! This constant specifies the number of subsequent detections of correct
 *  direction of rotation needed before the firmware is considered synchronized
 *  with the motor. (SYNCHRONIZATION_COUNT + 1) hall sensor changes in the
 *  same direction are needed.
 */
#define SYNCHRONIZATION_COUNT       2


//! Waveform status flag value for block commutation.
#define WAVEFORM_BLOCK_COMMUTATION    0

//! Waveform status flag value for sinusoidal driving.
#define WAVEFORM_SINUSOIDAL           1

//! Waveform status flag value for braking.
#define WAVEFORM_BRAKING              2

//! Waveform status flag value used in transitions between different types of driving.
#define WAVEFORM_UNDEFINED            3


//! The number to multiply speed input with to produce duty cycle compare value (0-255).
#define BLOCK_COMMUTATION_DUTY_MULTIPLIER   3


//! TURN_MODE value for coasting (disabled drivers).
#define TURN_MODE_COAST               0

//! TURN_MODE value for braking (low side braking).
#define TURN_MODE_BRAKE               1

/*! Turn mode. Set to either TURN_MODE_COAST or TURN_MODE_BRAKE.
 *
 *  \todo Select turn mode.
 */
//#define TURN_MODE                     TURN_MODE_COAST
#define TURN_MODE                     TURN_MODE_BRAKE


//! Speed control selection for open loop control.
#define SPEED_CONTROL_OPEN_LOOP     0

//! Speed control selection for closed loop control.
#define SPEED_CONTROL_CLOSED_LOOP   1

/*! Type of speed control. select either SPEED_CONTROL_OPEN_LOOP or
 *  SPEED_CONTROL_CLOSED_LOOP.
 *  \todo Select speed control method.
 */
#define SPEED_CONTROL_METHOD        SPEED_CONTROL_OPEN_LOOP
//#define SPEED_CONTROL_METHOD        SPEED_CONTROL_CLOSED_LOOP

/*! The number of ticks between each iteration of the speed loop.
 *  \todo Adjust speed control loop time base.
 */
#define SPEED_CONTROLLER_TIME_BASE   150

/*! PID controller proportional gain constant.
 *  \todo Adjust PID controller proportional gain. (Only for closed loop)
 */
#define PID_K_P    256

/*! PID controller integral gain constant.
 *  \todo Adjust PID controller integral gain. (Only for closed loop)
 */
#define PID_K_I    10

/*! PID controller derivative gain constant.
 *  \todo Adjust PID controller derivative gain. (Only for closed loop)
 */
#define PID_K_D    0

/*! The maximum increment (maximum speed) to use as setpoint when the maximum
 *  speed reference value is input.
 *
 *  \todo Adjust maximum increment. (Maximum speed, used by speed controller)
 */
#define SPEED_CONTROLLER_MAX_INCREMENT      620

/*! Max speed reference input. (Rounded up to closest power of 2 in this case,
 *  which is recommended to speed up division.
 *
 *  \todo Adjust Maximum speed reference input value.
 */
#define SPEED_CONTROLLER_MAX_INPUT          1024


static void SpeedController(uint16_t speedReference);
static void PortsInit(void);
static void PLLInit(void);
static void TimersInit(void);
static void PWMInit(void);
static void ADCInit(void);
static void PinChangeInit(void);
static void ExternalInterruptInit(void);
static void TimerSetModeBlockCommutation(void);
static void TimerSetModeSinusoidal(void);
static void TimerSetModeBrake(void);
static void BlockCommutationSetDuty(const uint16_t compareValue);
static uint8_t GetDesiredDirection(void);
static uint8_t GetActualDirection(void);
static void BlockCommutate(const uint8_t direction, const uint8_t hall);
static uint8_t GetHall(void);
static void DesiredDirectionUpdate(void);
static void ActualDirectionUpdate(uint8_t lastHall, const uint8_t newHall);
static uint16_t SineTableIncrementCalculate(const uint16_t ticks);
static void AdjustSineTableIndex(const uint16_t increment);
static void SetAdvanceCommutation(const uint8_t advanceCommutation);
static void EnablePWMOutputs(void);
static void DisablePWMOutputs(void);
static void CommutationTicksUpdate(void);
static void MotorSynchronizedUpdate(void);
static uint8_t IsMotorSynchronized(void);
static uint8_t SineTableSmallGetValue(uint8_t index);
static void SineOutputUpdate(void);
static unsigned int MultiplyUS15x8(const uint16_t m15, const uint8_t m8);


/*! \brief Set duty cycle in PWM6 mode.
 *
 *  This macro sets the duty cycle in PWM6 mode.
 */
#define TC1_PWM6_SET_DUTY_CYCLE(dutyCycle) TC1_WRITE_10_BIT_REGISTER(OCR1A, (dutyCycle))


#endif

⌨️ 快捷键说明

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