DC Motor Controller for CNC Router

DC motor rotational speed controller for Chinese CNC3040 spindle motor without any kind of encoder

Similar projects worth following
This Chinese CNC routers are arriving with a solid mechanics and with an electronics what can use some upgrade.
The spindle motor controller a standalone PWM with a potentiometer based rotational speed control. The running of the motor can't be controlled from the LinuxCNC/Mach3.
This project is for building a completely new driver for it.
1. Switching on/off from software
2. Control the rotational speed from software
3. Creating a closed loop control without encoder based measurement
4. Adding a digital RPM display

The project will be build upon the following things:

Some kind of MCU platform (not decided yet, most probably some ARM Cortex-M0 based one). This will provide the following functions:

1. Receive the control signal from the LinuxCNC/Mach3 trough the CNC control box isolated receivers. The control signal consist two parts: a switch on/off signal and a low frequency (10Hz) PWM proportional to the required rpm. This signal will be processed and the rpm value rounded to discrete values

2. Receive the current shunt monitor and the protection diode measurement signal. The actual load and the current rpm comes from it.

3. Acting as a PID rpm controller based on the required and actual rpm.

4. PWM generator for the switching MOSFET

5. Display driver for the RPM and Current displays

High Current MOSFET driver with current measurement capabilities based on my previous project:

Analog measurement front-end: the signal from the commutator is quite noisy. I'll need some analog front end to filter it before reach the ADC (or digital) input of the MCU

RPM measurement theory:

A motor is a highly inductive load. When the commutator switches from one coil to the next one the built magnetic field is not able to change as quick as the current changes. This generate negative voltage spikes on the motor poles. This spikes must be filtered out with a parallel diode. If we measure the current through this diode, we can find the these spikes and calculate the actual rpm from the frequency of it.

  • 1 × 48V/400W Brushed DC spindle motor
  • 1 × IRF9530 Discrete Semiconductors / Power Transistors and MOSFETs
  • 2 × 2N7002 Discrete Semiconductors / Transistors, MOSFETs, FETs, IGBTs
  • 1 × 48V/600W Industrial PSU
  • 1 × Microchip MCP6002 Amplifier and Linear ICs / Operational Amplifiers

View all 10 components

  • Front Panel Board Build

    SUF08/13/2015 at 13:39 0 comments

    More than a week ago the boards finally arrived:

    Then I soldered the parts into it:

    I picked one of my Nuvoton development board, cut it to it's parts, and soldered the missing headers, to be able to use it as an ICE programmer/debugger:

    Finally, I started to rewrite the controller's program, to the new pin configuration. During this process, I also want to little bit clean up the code.

    To test the board is working, I wrote a "Hello World" for it. :-)

    The board looks like working so far. The next step would be to finish the conversion/clean up the code.

  • Front panel design finished

    SUF07/20/2015 at 04:01 0 comments

    As I promised my previous post, I made some tweaks on the front panel schematics. To be precise, connected the push button of the rotary encoder to the MCU. This gives me the flexibility to use the rotary encoder to navigate in some kind of menu system (if I write some code for it), able to eliminate the additional physical controls (mode switch, calibration switch), and provide the possibility to add more function. Here is the modification of the schematic drawing (actually I can't insert the full page here - lack of resolution of the computer where I'm writing this actually. All of the drawings can be downloaded from the github repo)

    I think, the current schematic will be the final one, if I don't find any additional problems with it. So I designed the board:

    And ordered it form the

    Waiting to arrive...

  • Learning Chinese :-), front panel schematics

    SUF06/22/2015 at 13:33 9 comments

    Reverse Engineering the CNC control board

    During the weekend I was trying (still unsuccessfully, but I don't give up) to get the PWM signal generated by the LinuxCNC out from the parallel interface/stepper driver board.

    I would like to achieve without soldering (just to have some challenge).

    First of all, about the board.

    The machine arrived with a JP-3163B board in it, plus and additional stepper driver for A-axis. Actually, I'd like to keep this board and I want to get as many things I can out of it. The board in question is a version 3.9.

    What I found out, that the documentation widely available (and already mentioned by me earlier here), is not completely correspond to my board. Even, if I check the pictures of the boards in sale currently on the AliExpress and eBay, are the same as mine, but the documentation is the other (in fact for the v3.6).

    If we are talking about the stepper drivers, and the inputs that are the same, but the additional secondary relay, the spindle drive, the jumpers, or the LED's for the A-axis are totally different.

    The only information I can get is the Chinese text from the board itself (not to much).

    Part of the 3.6:

    And the 3.9:

    As you can see the upper has 3 jumpers and the lower has 5. (If you didn't realized, the fifth located next to the parallel connector.

    Actually I'm trying to collect as much information about the boards as I can. I found this text somewhere:

    现出售的是最新的JP-3163B V3.9版本,增加了延时启动功能和风冷功



    外:本店的手柄只支持以前的V3.7 V3.8 V3.9版本,V3.6版本是不能用



    Translated (google translate our friends):

    Is the sale of the latest JP-3163B V3.9 version, adds delay start function and air-cooled power

    Energy, delay start is to better protect the drive easy to damage (air to open, subject only to the Z-axis

    Direction of pull solenoid valve relay 2 output to air cooling, air cooling is off, do use relay 2) and the other

    Outside: We handle only support the previous version V3.7 V3.8 V3.9, V3.6 version is not used

    The handle, the handle when your customers buy buy engraving machine handle, contact with the store, understanding your purchase

    Whether the board can be used with JP-392Q control handle.

    This is far from perfect, but at least we can see that some changes in the cooling and the delayed start is added somehow to the spindle drive.

    About the LEDs, specially the upper three. On the original board I seen somewhere else English text stating the following:

    LED1 (Red) - PWR - Power

    LED2 (Green) - A-OR - A-axis direction

    LED3 (Green) - A-PU - A-axis step

    On my board:

    LED1 (Red) - 电源 - Power supply

    LED2 (Green) - 主轴 - Spindle (Pin 1 of the parallel port)

    LED3 (Green) - 使能 - Enable (Pin 14 of the parallel port)

    I also tried to get some information about the jumpers

    JP1 - 内 5V / 外隔离 - Within 5V / outer barrier (Internal 5V / External supply ???)

    JP2 - 使能开 / 关 - So able to open / close

    JP3 - 风冷开 / 关 - Air cooling on / off

    JP4 - 模拟量开 / 关 - Analog On / Off (When I switch this of the previous constant 10V disapear from the spindle control)

    JP5 - 手控开 / 关 - Manual on / off

    Some of the pins...

    Read more »

  • Logic PSU - Testing

    SUF05/31/2015 at 05:02 0 comments

    Yesterday I soldered the parts into the board, I realized three mistakes, what I made.

    The designed connectors are bigger, than what I wanted. So I 'll have 3,96 mm spacing connectors, instead of the 2,54 mm ones.
    Drilled a 1,5 mm holes for the connectors instead of the required 2 mm ones. Fixed easily.
    There is an additional LC filter at the output of the circuit. I designed a 100uF/6,3V B size tantalum capacitor into it, but I bought 100uF/10V D size ones. I was thinking. Is I not solder this now, will this prevent me from trying the circuit out. Not. So I just keep it this way, and buy new caps on Monday.

    As I finished the build, I wanted to test it. I was specially interested in the noise generated by the circuit.

    As I had no cap in the output LC filter I soldered an old 100uF cap directly to the testing 470ohm load resistor, and tryed to figure out the noise generated.

    It was so low that I can't find it in the enviromental noise picked up by my oscilloscope.

    And finally the output voltage is good enough.

  • Logic PSU

    SUF05/28/2015 at 22:27 0 comments

    In the mean time I designed the test circuit/board for the power supply of the low voltage parts of the circuit. The MCU, the measuring amplifiers, the display will run from 3.3V (I planed to use 5V supply originally, but the display I'm using is not able to run from it). This supply finally not as cheap I wanted to have. It was clear that I need a switching mode supply, and a chip with high voltage capability. I know that a few hundred milliamps is not to much, and the whole circuit is powered from the mains and not batteries. This is a good candidate for some three leg standard regulator or LDO, but...

    Always, that but.

    the whole circuit will run from a single 48V supply. Generating just 100mA with a standard regulator means you have to dissipate 4.47W on the regulator. In addition the standard three leg regulators are not designed for 48V input voltage.

    So the decision is to use HV buck regulator. Especially the LM2594HV-3.3 model from TI.

    I designed a circuit around it:

    And a PCB for testing:

    The finished board (population come later):

  • MCU Arrived

    SUF05/28/2015 at 13:51 0 comments

    When I started this project I selected Nuvoton's M054LDN for it. It has 16+4K FLASH what looked enough to me. I have an M0516LDN based development board in my hands, so I started to write the code on it. As the project advanced it become clear, that the code will not fit into the 16K. There is two factor behind it: the character table used for the graphic display, and the floating point library used by the PID controller.

    But there is a problem. At the local reseller I just found the M054LDN and the M0516LAN and not the M0516LDN. This A instead of D means something here. It is the revision of the device. Together with other changes the rev D. has FIFO capability on the SPI interface what I'm extensively using for the display driver, and really don't want to throw it away.

    So I looked around, and found what I needed on the AliExpress.

    It arrived also this week:

  • V2 Testing

    SUF05/28/2015 at 03:54 0 comments

    On the weekend, I finally get to run the first test on the V2 MOSFET driver.

    I just connected it to the bench PSU, and the MCU, added a resistive load (a 470Ohm/5W resistor) to it. Switched on, and...

    Nothing happened.

    Looked around, trying to find the error.

    On the input, the PWM signal was there.

    On the low side small FETs the signal was there.

    On the MOSFET's gate... nothing was there.

    I turned the board to see the soldering side...


    After soldering the MOSFET and the diode, it started to work perfectly.

  • V2 Boards

    SUF05/05/2015 at 09:05 0 comments

    I planed to build the new motor driver during the weekend, what unfortunately doesn't happened. It took an additional week. What I want to mention here, that together with the motor driver I also designed a new measurement circuit. This one is able to measure not just the rotational speed but the current (it was also in the previous but untested) and the voltage of the motor. In addition I included the necessary protection diodes what was left out from the previous one, and a configurable fifth order low pass filter to test the filter for the final design.

    Here is the schematic diagram:

    And the PCB design:

    The first weekend achievement - etching the boards and collecting the parts:

    A week later - the boards cut, populated:

    The next things to come (not necessarily in this order):

    • Test this two boards
    • Design a home made pcb for MCU+Display
    • Add additional filtering into the adjustable DC
    • Design and build the last missing piece - the high voltage input 3.3V PSU
    • Test and tune the PID controller code
    • Move to the final PSU from the lab supply
    • Put everything together - write the code for the rpm setting from G-Code
    • Write the code for the voltage/current/power measurement
    • Design and order the final boards
    • Build everything into the original controller box

  • MOSFET driver revised

    SUF04/25/2015 at 21:36 2 comments

    I was thinking, looking around a lot before I designed and built the current motor driver circuit. I wanted to use something cheep, something I can learn from.

    The current one is working, but I was thinking, how can I make it a little bit faster. When I designed the current one, experimented lot on the breadboard, but not used ltspice to simulate the circuit. When it was finished, I needed to tweak it, here and there, to be able to reduce the noise for the clear measurement signal.

    Now I'm trying to get faster switching, to reduce the heat generated by the MOSFET.

    First of all I run a simulation of the original circuit.

    The circuit:

    And the result:

    As you can see the the timing results:

    Switch on time: ~500ns

    Switch off time: ~500ns

    After 2-3 weeks of continuous (in my spare time, what I not really have to much) simulation, changing components, pursuing different ideas, finally I created a little bit better one.

    The circuit:

    And the result:

    And the timing:

    Switch on time: ~30ns

    Switch off time: ~100ns

    Much better.

    Based on the things above, I designed a little bit different circuit. The reason: I use mostly trough hole components for the home made PCB and switch to SMD when I order the final one.

    The schematic

    And the PCB design:

    Hopefully I'll be to build it during the weekend.

  • The MCU control works!

    SUF04/06/2015 at 22:05 0 comments

    Since the last post regarding my CNC Motor Driver, in my spare time I was continuously working on the MCU board and the software for it.
    Two days ago I connected the digital part to the power electronics. It started to work immediately, but unfortunately the rpm measurement was messy.
    After some thinking and trying, I realized, that the source square wave has some narrow pulses around the edges, what are messing up my measurement.
    The Nuvoton MCU I'm using is able to add some de-bouncing delay to the timer's capture input. Adding this feature looks like solving my problems.

    Today finally I see the end of this project's. I'm trying to collect the thing still need to be finished:
    • Test and tune the PID controller
    • Try out additional filtering on the power input side
    • Try out additional filtering at the motor
    • Try out the 5th order filter I designed for the measurement
    • Test and write code for the current measurement
    • Add voltage measurement solution (circuit and code)
    • Add code for power display
    • Add code for measuring the control signal from the Linux CNC (this allows the control of the rotational speed from g-code)
    • Design a high voltage input 3.3V power supply (actually the 48V input is to much for the regular buck converter chips)
    • Design and order (hopefully) the final panel for the whole electronics
    • Correct the code for the rotary encoder (it is a little bit problematic today)
    • Clean up the code (not modularized enough, many comments missing)

View all 14 project logs

Enjoy this project?



Johnny wrote 07/25/2015 at 06:50 point

I really like what you've done! I had never thought of counting commutator spikes to derive rpm. I always used an encoder. Clever stuff. I'll be keeping an eye on this project, as I may design a similar spindle controller for my 3040 one day. Thanks for sharing your work. 


  Are you sure? yes | no

Andrew wrote 05/16/2015 at 07:53 point

Solid project, breh. Looking at the inherent multiplexed commutation effect is a neat approach.
Did you consider a more standard approach, like setting a 95-99% maximum DC PWM and sensing the back-EMF of the motor while it is coasting in that last 5-1% ? I have used this technique on very small motors (6mm diameter), and it works well.

I'm sure you know more than me about power electronics and switching and such, but I believe there are a panoply of single-chip MOSFET drivers that can be had pretty cheap. Bootstrap caps, charge pumping, all N-channel bridges, isolation, logic level driver, stuff like that. (like I said, I only know the overtones, not the details)

  Are you sure? yes | no

SUF wrote 05/16/2015 at 20:14 point


Thank you for your comment. To be honest, I wasn't aware of the back-EMF measurement method. Now I looked into it a little bit. As I'm not getting expert of it, I see some things in it, what I don't like. Please correct me, if I misunderstood something or have false assumptions:

1. The method measure the generated voltage of the motor, what is proportional to the rotational speed. This technique has some uncertainty in it, because of the motor parameters and the noise.

2. As I seen in the sources on the internet, this approach is for no load situation. If I go further with it, may work in constant load situation (I mean mechanical load here). But the CNC spindle is usually not under constant load situation. This lead me to take also the current of the motor into the equation (what is proportional to the mechanical load), creating a more complex equation and introducing more uncertainty into the measurement.

On the other side my method has no relation to the load, the voltage, or the measurement point, it clearly derived from the position of the commutator segments, and the inductive spike generated from it.

This is about the measurement side.

If we talking about the circuit complexity, the back-EMF method has clear advantages:

1. It can work on lower frequency control. The commutator measurement require relatively high frequency, because of he following reasons: need a room in the frequency domain for filtering out the switching noise of the MOSFET driver, to keep the size of the inductor/capacitor of the buck circuit low. Using lower frequency have clear advantages: 

Less complicated MOSFET driver. Even a single low side logic level N-Channel MOSFET would be sufficient

Finer PWM adjustment capability. In my current system I use an MCU, what is able to work with 25MHz base frequency for the PWM timer. This gives me 250 steps of control in 100kHz. If I can lower the control frequency to let say 10kHz the result will be 2500 control step. In the current approach, if I want, to higher the PWM frequency or increase the number of steps in the pulse width, I can easily find myself in the world of the pikosecond timers.

2. Eliminate the buck storage circuit. Even it can't be there, otherwise the measurement will be impossible

About the MOSFET control. I'm not an expert in this field either. In the beginning, I just wanted to create an easy N-Channel low side driver. As I was digging deeply into the measurement problem, I realized, that I need to build something looks much more like a Buck mode SMPS  than a MOSFET switch.

You right that you can cheaply buy an integrated high side MOSFET driver for almost nothing. This drivers are able to drive an N-Channel MOSFET on the high side with bootstrap capacitor. And yes the N-Channel MOSFETs having better electrical parameters than the P-Channel in use here.

To go further, you can even buy half bridge controllers for nuts instead on the high side driver achieving better results with synchronous buck mode. Even I was trying to use ST's L6384E, in this circuit. But...

Always a but... somewhere. :-)

The required load of max 10A can be easily handled with relatively good P-Channel MOSFET (it has less than 1nF gate capacitance, the low gate capacitance is a key element here).

The L6384E (basically the only half-bridge controller can be purchased here for reasonable price - didn't wanted to take into consideration the free engineering samples keeping the whole design easily rebuild able to anybody wish  to), was not able to go far beyond the 20kHz mark, because of the required dead-zone setting.

But the key decision factor was not the two points above. This was the question of the 100%. If you want to achieve 100% on the PWM side, the bootstrap capacitor gets useless. There will be no time when you can charge it, and the leakage of the capacitor and the MOSFET1s gate will discharge it fast. If you need 100%, your choice of integrated controllers suddenly gets limited. You need something from this moment, what has a boost converter, or a charge pump, instead of the bootstrap capacitor. I only found two chips (maybe more exists), what was suitable to the task. One from Linear, and one from Allegro. The first one was highly priced, the second was only available from ebay/aliexpress.

Sorry for being so long. I hope it was not offensive. I just wanted to clarify my thoughts and research behind my design decisions.


  Are you sure? yes | no

Andrew wrote 05/17/2015 at 05:55 point

The loading situation of the motor shouldn't matter, since the measurement is being done with the motor electrically disconnected from the rest of the circuit. This is also called the "speedance" of the motor, the voltage induced as a function of speed. It should work down to low speed.

Yes, it is a bit noisy, but with median filtering and window averaging, you can get good average speed control. If you want to be really fancy, you could just have both methods, and cross over, or do a combined estimator between both!

You'll need to divide and offset the motor BEMF from (-48,+48)v down to (0, 3.3)v. Or if you have a symmetric supply into your ADC, maybe (-3.3,3.3).
Here is the circuit I used to transform (-4.2,4.2)v to (0,3.3)v:
(actually, a little more than 0, and a little less than 3.3, so there is no clipping).

Choosing the PWM frequency for your motor is a design problem of its own, there is probably a good application note on it somewhere. I believe the problem with high frequency is that it won't allow current to actually build in the motor, and there will be inductive effects. The disadvantage of low frequency is audible noise, and possibly not smooth control.

So, maybe try driving the spindle and measuring the time the BEMF signal to stabilize when the switches open. For 48v and this big a motor, the recovery time might completely preclude the BEMF approach.

  Are you sure? yes | no

SUF wrote 05/18/2015 at 12:20 point

Hi Andrew,

I want to finish the work on my current setup, but definitely want to try out BEMF later. I see both the advantages and disadvantages of both. 

Thank you for enlighting me.


  Are you sure? yes | no

Hacker404 wrote 05/16/2015 at 06:21 point

I was intending to make a DC motor direct RPM motor control unit at a later stage when I start with my plans for a CNC router. 

My approach would be to just have a capacitor from the back EMF side (motor) to a zero crossing rate sensor to a MCU (uC) interrupt. Very few components cheap and effective. The only intimation you need is frequency (ie zero crossing) and some indication (rate of crossing) that distinguishes this from noise. Load current is handy but not essential as there is no G code that relates to load. A stall is still detectable with just the above information.

  Are you sure? yes | no

Similar Projects

Does this project spark your interest?

Become a member to follow this project and never miss any updates