# FOC for a BLDC motor with Hall sensors but no encoder

I am trying to implement a FOC algorithm in an MCU to use with a BLDC motor.

My problem is that I only have the Hall sensor feedback, no precise encoder can be used. With this 4 pole pairs motor, Hall sensors give 15 degree resolution.

I think this is the reason my algorithm is failing and I cant get a DC constant d and q values.

Is there any better way to drive a BLDC motor than FOC? What I need actually is a way to feed torque/ current to the regulator and be able to precisely read the feedback.

My analog circuitry for measuring $I_a$ and $I_b$ currents works fine, I just don't know how to calculate the needed feedback value.

In other words, can FOC even work for BLDC without an encoder but just with Hall sensors? If not, what is the better way?

My analog circuit:

• Do you have any other sensors in the drive circuit? Can you sense back EMF or current anywhere in the bridge? Can you add a schematic to show what Ia and Ib are? Oct 3, 2016 at 15:18
• I can sense the a and b phase currents (low side current sensing). Oct 3, 2016 at 15:19
• You cannot sense the phase voltages? Oct 3, 2016 at 15:51
• No, not really I gues. I have added my measure circuit diagram to the post. Oct 3, 2016 at 15:52
• Thats true but taking this under consideration is far ahead of me for now Oct 3, 2016 at 16:15

can FOC even work for BLDC without an encoder but just with Hall sensors?

You have an encoder, it just doesn't have very high resolution. But how to increase it?

Once you know how fast the rotor is spinning (time between Hall sensor signal changes) you can predict intermediate angles. If motor speed is changing then the prediction will be off, but you can compensate for this too by measuring the acceleration and factoring it in.

• The problem is the speed value measured from the peripheral timer seems to be really jerky. I had to use low pass filter in order to stabilise it a bit. Oct 3, 2016 at 16:40

It is rather hard to think of such a system without carving out a shaft position/velocity estimator as a separate concept whose properties you can adjust independently of the other components.

The estimator would update the position/velocity estimate each time you update the control loop. The inputs to the estimator are passage of time (e.g. control loop ticks) and the Hall input changes. Expressed in C++, the estimator's API would look as follows:

class ShaftEstimator {
...
float m_angle = 0., m_speed = 0.;
/// Initializes the estimator with null angle and speed
ShaftEstimator();
/// Called every loop tick. Updates the angle and speed.
void update(bool hall_a, bool hall_b, bool hall_c);

The estimator doesn't need access to any hardware: the API above is all you need to interface it with the rest of the system. Since update() is called periodically at a fixed rate, the estimator can keep track of how many ticks it took the shaft to rotate between Hall state changes. You could apply filtering commensurate with the ratio of the inertia in the system vs. expected disturbing torque (whether generated by the motor or applied externally), you could also make a more complex estimator that uses the torque generated by the motor to estimate the effective inertia of the motor system and applied external load torque. None of it is particularly complicated; here you have a starting point that clarifies how the interface of the estimator should look.