Hello,
I reference the document AN4704 and code to do research of Sensorless Control of BLDC Motors use MC9S12ZVM .And in the code as follow:
I do not know: why SPEED_CALC_NUMERATOR=16777216? 1431.655765 = 1000 rpm? How to calculation it ?
Thanks!
#ifdef _HIGH_SPEED_SCALING
/***** High speed scaling *********************
* For 4 pole-pairs motors
* Boundary values for 1.28 us timer period:
* - Minimal speed: 60 rpm
* - Minimal speed scaled: 86
* - Maximal speed: 22887 rpm
* - Maximal speed scaled: 32767
*********************************************/
#define SPEED_CALC_NUMERATOR 16777216
#define STALLCHECK_MIN_CMT_PERIOD 97 // 97 = 125 us (20 krpm on 4 pole-pairs motor), min value = 85 (22.89 krpm)
#define REQUIRED_RUN_SPEED 1432 // 1431.655765 = 1000 rpm
#define MIN_SPEED (1432/2) // 500 rpm minimal speed for Down button control (should be min 10% of nominal motor speed)
#define MAX_SPEED (1432*13) // 13 krpm maximum speed for Up button control
#define SPEED_STEP (1432/2) // 500 rpm, Up/Down step for button controls
//*****
#endif
period6ZC = periodZC_F_PhA + periodZC_R_PhA + periodZC_F_PhB + periodZC_R_PhB + periodZC_F_PhC + periodZC_R_PhC;
actualSpeed = SPEED_CALC_NUMERATOR / period6ZC;
Solved! Go to Solution.
Hi,
The numbers make the connection between the commutation time and speed in terms of Timer ticks.
If the floating point representation is used, it's agreed that the math between speed and commutation period is given:
Speed_RPS = 1 / (CommutationPeriod * PolePairs)
CommutationPeriod = 1 / (Speed_RPS * PolePairs)
Speed_RPS = Speed_RPM / 60
In 1.15 fractional implementation <-1.0, 1.0), the situation is scaled to a "numerator", which helps the calculation to stay within the scale, considering integer type casting.
tFrac16_Speed = tU32_Numerator / (tU16_CommutationPeriod * tU16_PolePairs)
tU16_CommutationPeriod = tU32_Numerator / (tFrac16_Speed * tU16_PolePairs)
While we typically use higher pole-paired motors, the numerator should be calculated based on the pole-pairs.
Some advanced math behind:
We can start with the maximal speed, let's say MaxSpeed = 15000 RPM and PolePairs = 4. That means, the CommutationPeriod = 1 / (15000/60 * 4) = 1 ms
Let's set the minimum number of timer ticks per one commutation, which gives us a precission of the commutation:
MinTicksPerCommutation = 512
Now, our system uses 1.15 fraction format, which means the maximum integer number is ideally 32768. This gives us the base for our Numerator:
tU32_Numerator = MinTicksPerCommutation * 32768 = 16777216
With the minimal CommutationPeriod = 0.5 ms and MinTicksPerCommutation = 512, we can calculate the timer domain:
MaxTickTime = MinCommutationPeriod / MinTicksPerCommutation = 1.9... us. Now, the fBus divider is calculated, based on the fBus = 50 MHz
TimerDivider ~ MaxTickTime * fBus = 96., thus nearest TimerDivider = 64
TimerTickFrequency = fBus / TimerDivider = 781.25 kHz
TickTime = 1.28 us
Since we have selected a different TimerDivider, the scale is slightly different for corner case:
MinCommutationPeriod = TickTime * MinTicksPerCommutation = 1.28us * 512 = 0,655 ms
MaxSpeed = 1 / (MinCommutationPeriod / 60 * 4) = 22 900
In the example, the speed is calculated simply by adding all the commutation periods and recalculating using the formula above.
For the speed scale, just consider following:
tFrac16 maximum is 32767
MaxSpeed is 22900
If the required speed is 1000 RPM, its integer representation is then 32768 / 22900 * 1000 RPM = 1431 RPM
I hope it will help.
Best regards,
Matej
Hi,
The numbers make the connection between the commutation time and speed in terms of Timer ticks.
If the floating point representation is used, it's agreed that the math between speed and commutation period is given:
Speed_RPS = 1 / (CommutationPeriod * PolePairs)
CommutationPeriod = 1 / (Speed_RPS * PolePairs)
Speed_RPS = Speed_RPM / 60
In 1.15 fractional implementation <-1.0, 1.0), the situation is scaled to a "numerator", which helps the calculation to stay within the scale, considering integer type casting.
tFrac16_Speed = tU32_Numerator / (tU16_CommutationPeriod * tU16_PolePairs)
tU16_CommutationPeriod = tU32_Numerator / (tFrac16_Speed * tU16_PolePairs)
While we typically use higher pole-paired motors, the numerator should be calculated based on the pole-pairs.
Some advanced math behind:
We can start with the maximal speed, let's say MaxSpeed = 15000 RPM and PolePairs = 4. That means, the CommutationPeriod = 1 / (15000/60 * 4) = 1 ms
Let's set the minimum number of timer ticks per one commutation, which gives us a precission of the commutation:
MinTicksPerCommutation = 512
Now, our system uses 1.15 fraction format, which means the maximum integer number is ideally 32768. This gives us the base for our Numerator:
tU32_Numerator = MinTicksPerCommutation * 32768 = 16777216
With the minimal CommutationPeriod = 0.5 ms and MinTicksPerCommutation = 512, we can calculate the timer domain:
MaxTickTime = MinCommutationPeriod / MinTicksPerCommutation = 1.9... us. Now, the fBus divider is calculated, based on the fBus = 50 MHz
TimerDivider ~ MaxTickTime * fBus = 96., thus nearest TimerDivider = 64
TimerTickFrequency = fBus / TimerDivider = 781.25 kHz
TickTime = 1.28 us
Since we have selected a different TimerDivider, the scale is slightly different for corner case:
MinCommutationPeriod = TickTime * MinTicksPerCommutation = 1.28us * 512 = 0,655 ms
MaxSpeed = 1 / (MinCommutationPeriod / 60 * 4) = 22 900
In the example, the speed is calculated simply by adding all the commutation periods and recalculating using the formula above.
For the speed scale, just consider following:
tFrac16 maximum is 32767
MaxSpeed is 22900
If the required speed is 1000 RPM, its integer representation is then 32768 / 22900 * 1000 RPM = 1431 RPM
I hope it will help.
Best regards,
Matej
Hello Matej,
Thank you very much!