This page is intended to help people who wish to build / operate a 3 axis CNC router. It discusses software compatible with commercially available controller boards and a raspberry pi computer. It specifically discusses using the bCNC program on the raspberry pi to communicate with the microcontroller running grblHAL. Please note that CNC milling is not my area of training, that my experience here is very limited and that this page reflects my experiences and opinions, some of which may be catastrophically wrong. Your mileage may vary. If you see glaring errors, feel free to point them out to me (j6summers@gmail.com).
Size matters (so does budget).
The build plate on our machine is about 400 mm square. Here is a link to a design that you can build to handle 4 foot by 8 foot sheet goods. Each design has its advantages and disadvantages. The stiffness of a machine is another consideration. Milling wood or plastic can be done with a relatively flexible machine but milling aluminum requires greater stiffness. Milling steel requires much greater stiffness and is beyond our experience.
A smaller machine will be stiffer than a larger one but will limit the size of what you can make. A machine made from aluminum extrusions will not be as stiff as one made from cast steel but it will be an order of magnitude less expensive. Consider what you want to use the machine for. A machine for cutting small bits of wood will be a lot less expensive than one for milling large pieces of steel.
Our 3 axis CNC mill was assembled from a kit we bought from OpenBuilds. While OpenBuilds is no longer in business, here is a link to a hardware kit by another manufacturer that is based on the same design. Here is a video showing how it is assembled. The machine is made from aluminum V-slot rails, which are available from a number of online suppliers. MakerStore.cc is one such supplier. MakerTechStore.com is another. In addition to the aluminum rails, the build requires the following: 1. gantries that ride on wheels along the rails, 2. plates at the ends of the gantries that accept the drive screws and motor hardware, 3. drive screws, nuts, bearings and standoffs for the motors, 4. motors (NEMA 23 steppers) and couplers (that connect the motors to the drive screws, 4. a small router and mounting hardware, 5. a hefty power supply (we use 24V DC) and 6. a controller board (we use the T41U5XBB with a Teensy 4.1 microcontroller which was one of the earlier available for grblHAL), and stepper motor drivers. Of course, you need a computer to drive it. We use a Raspberry Pi model 4b.
We also built a plywood box to keep the noise and sawdust down. Sawdust made out of aluminum chips is especially hard on electronics. Don't ask how I know.
There are two types of motors used for spindles, brushed and brushless. On our current machine we use a small (1.25 hp) Makita router with a brushed motor. This works well for cutting wood products and plastics, and can be used to cut aluminum. It is not, however, ideal for all uses. Routers run at crazy high rpm. Cutting metals requires a slower turning spindle with speed control, which is something brushless DC motors (bldc) do. A brushless DC spindle requires a Variable Frequency Drive (VFD) with a DC power supply. It may need a water pump for cooling and you will need a mount for the spindle. Here is a link to a spindle kit that I am considering. For cost comparison, in February 2026 the spindle kit cost $255 while the Makita router was $150.
There are ways to slow down a router. Here is a commercial device that retails for $150. Here is a link to a discussion of building a speed controller for a router.
The controller board takes instructions (GCode) from your host computer and runs your stepper motors, turns on the spindle, monitors the end stops, etc. As mentioned above, we use the T41U5XBB driver board with the Teensy 4.1 microcontroller. Since we built our current configuration, a number of other boards have become available.
One thing that I do not like about the board we currently use is that it requires external motor drivers. More recent controllers incorporated mounts for driver boards. The most recent tend to have drivers incorporated.
I am currently building a second CNC router for larger wooden projects based on the LowRider from V1 Engineering and I plan to use the rodent board from BTT (screen shot above) to use as the controller. This board incorporates the ESP32 microcontroller, has WiFi capability, and has incorporated motor drivers capable of sourcing 3A of current. The grblHAL firmware for this board can be built using the web builder.
As an add-on, we built a jog-controller (described in the next section) that allows us to jog the tool around without sitting in front of the computer. The jog controller connects to the I2C interface pins, which are broken out on our current controller board.
Since our machine is in a plywood box, it is not easy to see the position of the cutter while sitting at the control computer. The jog controller (photo on the left) allows me to jog the tool around while physically in front of the router. The controller incorporates a RPi Pico microcontroller on the back of the pcb and a bunch of buttons on the front. The Pico communicates with the router controller using the I2C protocol. The grblHAL firmware is already set up to interface with a keypad, but requires that you include the "keypad" plugin when you compile. This is easily done using the web builder (described below in the Firmware section). The jog controller has buttons to jog in X, Y, and Z (plus and minus) and also 45 degrees between the x and y axes (+X+Y, +X-Y, -X+Y and -X-Y). It also has a button to toggle between three jog speeds (rapid, slow, and step). The oled display shows the current jog speed setting.
The first thing you need is a program that talks to the microcontroller on the driver board. A program called bCNC works well on the Raspberry Pi. You can download bCNC for free. While the instructions for installing the code are basically correct, downloading packages onto the current Pi operating systems requires you do so in a virtual environment. Here is a description of how that is done.
Like other CNC control software, bCNC has a terminal function that allows you to look at the code passed between the computer and the machine. In this terminal (accessed on the upper right tab) you can view and edit a number of machine settings. To view the settings, type $$ in the command line. Here is a page to help understand what the settings are.
The firmware you need will depend on the controller you use. Our present machine uses the Teensy 4.1 microcontroller with grblHAL firmware. One benefit of grblHAL is that you can download compiled firmware from a web builder. For the Teensy microcontroller, the web builder outputs a hex file that can be loaded using the Teensy Loader application.
The web builder has a number of tabs that allow you to customize your software. One of the tabs is "plugins". On the plugin tab you can chose to enable the keypad functionality. Even if you don't have a keypad, it doesn't hurt to have this enabled in case you decide you want one later. For my planned larger machine, I intend to use ganged Y axis motors that allow auto-squaring. Auto-squaring is an option available through the web builder. Another option is a Z-axis probe.
Another popular firmware is FluidNC which was written for ESP32 microcontrollers. The rodent controller I purchased incorporates the ESP32, so I will have the option of pursuing this in my future build. According to this link, grblHAL can be flashed onto the ESP32 using a tool from here. Here is a link to a page describing how to use the tool
Setting up your CNC router requires getting the machine settings correct. The settings include things like the number of steps the microcontroller sends to make the machine move a certain distance. To find the machine settings, type $$ into the terminal. grblHAL will respond by sending a list of machine settings and their values. Unfortunately, grblHAL does not give a description of what each setting is in this list (I think that Universal GCode Sender, UGS, does). Here is a link to a page with a listing of settings.
Common Errors: Once you load up the firmware, grblHAL is expecting normally closed limit and probe switches. If you use normally open limit switches, you will get error message from bCNC that say: "XYZHSEP". These are seven individual error messages that are associated with not having the expected hardware configuration. You can fix these by opening the terminal and sending the following commands: $5 = 7 (this inverts the x, y, and z end stops, fixing the X, Y, and Z errors). Sending $14 = 70 inverts the emergency stop (E), hold (H) and start (S) switches. Sending $6 = 1 inverts the probe switch, fixing the P error.
The fast and easy way to get from idea to product is to throw money at it. That is not what we do and I am not going to pretend to know the ins and outs of what is involved. Here is a review of some options. Autodesk Fusion offers a version with limited functionality for personal use is free for 3 years. After that, I assume that you need to pay for it. VCarve also has free versions and time limited options.
The first step in CNC milling is drawing what you want planned. This is done in Computer Aided Drafting (CAD) programs. While there are a number of good CAD programs for generating .stl files for 3D printing, this doesn't easily translate to CNC milling. Inkscape is a commonly used program for creating 2 dimensional drawings. It is not something I have experience with. One option is LibreCAD. Another option is a python based, open source program called EZDXF that has a plugin (r12writer) that allows you to generate dxf files. Once you have a two dimensional drawing, you can translate that into GCode using CAM software.
CAM is an acronym for Computer Assisted Manufacturing. Here is a reddit page that discusses some of the options.
While 3D printing usually uses .stl files, milling requires files written in GCode. Some programs require files in DXF format. We have used a program built into our controller software (bCNC). The CAM functions of bCNC are not intuitive and it takes a bit of time to figure out how to use them. Documentation is rather limited, but here is something to get started. Here is a link to a web based DXF to CAM program. Here is a link to a tutorial for using a program called FlatCAM to generate tool paths for milling pcb boards.
PyCAM, a cautionary tale: One CAM program that looked promising is PyCAM, an open source python based program that works with Linux. Pycam has a problem with one or more of the modules being deprecated. This is discussed in a pull-request from the GitHub page. As far as I can tell, PyCAM is not functional.
GCode can be generated from drawing files (usually in DXF format) by a number of programs. Here is a link to a web page where you can download a program for converting DXF files to GCode. Here is a link to an online program available from the folks at OpenBuilds. Here is another online program.