Are you creating a cloud-connected IoT device for commercial use that’s inexpensive, works with all kinds of sensors, and lasts for a long time on battery power? (中文版)
You can buy the Blue Pill microcontroller for under US$ 2. That’s even cheaper than Arduino Uno. And yet the Blue Pill has a faster processor (based on 32-bit Arm Cortex-M3), supports more input/output ports: UART (3 ports), SPI (2 ports), I2C (2 ports), USB and CAN Bus, operating on 37 General Purpose I/O (GPIO) pins.
Like the Arduino Uno, the Blue Pill is developer-friendly, with open source libraries and sample programs available. What’s the catch? Developer tutorials for the Blue Pill are scarce right now, because the Blue Pill is a recent “invention” by the brilliant hardware engineers in China (although the overall STM32 ecosystem is already very well established).
In this tutorial I’ll give you all the info and (free, open) source code you need to build your own IoT device based on Blue Pill, with real sensors, and connect it to the Sigfox network. By the end of the article you’ll know all about…
- Getting the Blue Pill dev kit
- Connecting Blue Pill to sensors and Sigfox transceiver
- Intro to Blue Pill programming and cocoOS multitasking library
- Compiling, running and monitoring programs on Blue Pill
- Using free open-source dev tools: Visual Studio Code and PlatformIO
- Configuring the Sigfox Backend for uplink and downlink messaging
- Soldering tips for Blue Pill
We’ll take the Blue Pill and transform it into a simple IoT device for environmental monitoring that sends temperature, humidity and altitude data to the Sigfox network every few minutes.
The complete source code may be found here…
IoT program for Arduino Uno / STM32 Blue Pill (libopencm3) that reads BME280 temperature + humidity + altitude sensors…
If you have been following my past articles, you might find the topics here familiar. I have consolidated all the past topics on Blue Pill development and Sigfox connectivity into this single tutorial. Even if you haven’t read my previous articles, just follow me as we walk through each step…
Prepare The Hardware
To try out the Blue Pill code in this tutorial, we’ll need…
1️⃣ Blue Pill: Buy online at AliExpress. Search for
stm32f103c8t6 development board
2️⃣ ST-Link V2 USB Debugger (about US$ 2): Connects the Blue Pill to your computer (via USB) to flash the compiled program into the Blue Pill. Buy online at AliExpress, search for
3️⃣ [Optional] SparkFun BME280 Sensor: Our Blue Pill will send actual temperature, humidity and altitude data from the BME280 sensor. If you don’t have the sensor, we can configure the program to send simulated sensor data instead.
4️⃣ [Optional] Breakout Board for Wisol Sigfox Transceiver: Our Blue Pill will transmit sensor data to the Sigfox network via the Wisol WSSFM10RxAT module.
If you don’t have the breakout board, the program can simulate the sensor data transmission to Sigfox.
To buy the Wisol Sigfox Breakout Board, browse the official list of Sigfox developer kits and click the
Zone box to filter by your region (e.g. Sigfox Zone
RCZ 1 for Europe,
RCZ 2 for US).
Choose a breakout board that’s based on Wisol WSSFM10RxAT (where “x” denotes 1, 2, 3 or 4 for the four RCZ zones). And it should be powered by 3.3 volts, not 5 volts.
You may also buy the Wisol Sigfox Breakout Board from the Tindie marketplace:
Breakout Board of WISOL Module for SIGFOX Network by Upton's Gadgets on Tindie
Breakout Board of WISOL Module for SIGFOX Network from Upton's Gadgets on Tindie
If you can’t find a suitable Wisol Sigfox Breakout Board, you could build your own.
I have published the PCB design for a breakout board in Autodesk EAGLE CAD and Gerber formats.
The design should work with Wisol Sigfox modules for
RCZ 1, 2, 3 and
4 (although I have tested only one board for
Schematics for Wisol WSSFM10R Sigfox Breakout board - lupyuen/Wisol-WSSFM10R-Sigfox-Breakout
If you’re making your own breakout board, remember to get the right U.FL antenna for your region: 868 MHz for
RCZ 1 (Europe and Middle East), 902 MHz for
RCZ 2 (US), 923 MHz for
RCZ 3 (Japan), 920 MHz for
RCZ 4 (Australia, New Zealand, other parts of Asia).
I have tested this antenna for
RCZ 4 (the one at the top of the photo).
Important: Always connect your antenna to your Wisol Sigfox Breakout Board before powering on the Blue Pill. Otherwise you may damage the Wisol module!
Connect The Hardware
Follow the above diagram to connect the Blue Pill to the Wisol Sigfox Breakout Board and to the BME280 sensor…
Blue Pill Pin PA4 (SS1) → BME280 Pin !CS
Blue Pill Pin PA5 (SCK1) → BME280 Pin SCK
Blue Pill Pin PA6 (MISO1) → BME280 Pin SDO
Blue Pill Pin PA7 (MOSI1) → BME280 Pin SDI
Blue Pill Pin 3V3 → BME280 Pin 3.3V
Blue Pill Pin GND → BME280 Pin GNDBlue Pill Pin PA2 (TX2) → Wisol Pin RX
Blue Pill Pin PA3 (RX2) → Wisol Pin TX
Blue Pill Pin 3V3 → Wisol Pin 3.3V
Blue Pill Pin GND → Wisol Pin GND
Note that the Blue Pill ships with the header pins unsoldered. Check the soldering tips at the end of this article.
Connect the Blue Pill to the ST-Link USB Debugger.
Note: For the ST-Link, only the bottom row of pins is used. The Micro USB Port of the Blue Pill doesn’t need power — the BME280 sensor and the Wisol Sigfox Breakout Board will be powered by the ST-Link.
Ensure that both yellow jumpers on the Blue Pill (
BOOT1 near the Micro USB Port) are set to the “
0” positions (closer to the Micro USB Port).
Don’t connect the ST-Link to your computer yet, we need to install the Windows drivers for ST-Link, as described below.
For a complete list of pins on Blue Pill and their functions, see this pinout diagram.
Install The Software
Follow the steps below to install OpenOCD (the software that connects to the ST-Link Debugger and displays the debug log for the Blue Pill) and the ST-Link USB Driver (for Windows only)…
- Download OpenOCD from the
► Unofficial OpenOCD release website
- Unzip the downloaded file and copy the OpenOCD files into
openocd.exeis located in the folder
- Download the ST-Link USB driver from the
► ST-Link Driver Website (email registration required)
- Unzip the downloaded file. Double-click the driver installer:
► Brew Website
- Enter the following in a command prompt:
brew install openocd
- Install the
udevrules for the ST-Link
- Enter the following in a command prompt:
sudo apt install openocd
Download The Source Files
Open a Windows, Mac or Ubuntu command prompt and enter:
(For Windows, install
git from Git For Windows)
git clone https://github.com/lupyuen/send_altitude_cocoos.git
Then enter the following into the command prompt…
For Mac and Ubuntu:
chmod +x scripts/*.sh
This creates symbolic links for the source files inside the
src folder, and replaces the default cocoOS configuration
os_defines.h with our own. Also this installs a subset of the Boost library used by the program (UART Interface specifically).
Install Visual Studio Code and PlatformIO
Download and install Visual Studio Code from
► Visual Studio Code Website
For Windows, choose the
Launch Visual Studio Code.
In the left menu bar, click the
Install the following extensions:
- PlatformIO (by PlatformIO — see above)
- C/C++ (by Microsoft — see below)
Install button is missing for the C/C++ extension, then it’s already installed.
After installing, click
Reload to restart Visual Studio Code
File → Open Workspace
Browse to the
In a while you should have a fully configured Visual Studio Code workspace with PlatformIO. In the
Workspace pane at left, double-click on
platform.hand uncomment the following line so that you’re using the right features for this article…
#define CONFIG_ARTICLE5 // Uncomment to support Article #5
Check that the other
#define CONFIG_ARTICLE... lines are commented out.
Workspace pane at left, double-click on
main.cpp and you should see this…
How Does The Program Read Sensors?
Let’s pause and look at
main.cpp. This is the main C++ program that runs on the Blue Pill.
Remember for Arduino the system functions are defined in the
Arduino.h library? For Blue Pill we use the open source library
libopencm3. You’ll see
libopencm3 included at the top of
To demonstrate how we may read multiple sensors concurrently on Blue Pill (since it’s powerful enough to do so), the program uses the cocoOS multitasking library.
Recall that the BME280 can provide 3 sensor values: temperature, humidity and altitude.
The program creates 3 Sensor Tasks to read the values, one task for each sensor…
Each Sensor Task contains the code to read the sensor value, in the
poll_sensor() function. For example, the
poll_sensor() function in the Temperature Sensor Task calls the
bme.temp() function (from the BME280 library) to read the temperature value from the BME280 via port
What happens to the returned sensor values: temperature, humidity, altitude? The Sensor Task creates a Sensor Data Message (thanks to the cocoOS library) and transmits the message to the Network Task…
The Sensor Task loops forever reading the sensor and transmitting the sensor value (after pausing 10 seconds).
cocoOS also provides Semaphores to ensure that our Sensor Tasks won’t clash when reading the same I/O port, like the SPI1 port connected to BME280.
More about Semaphores in this article.
Thanks to cocoOS our sensor code is clean and efficient!
How Do We Transmit Sensor Data To Sigfox?
Recall that the Sensor Task sends Sensor Data Messages to the Network Task.
The Network Task (source code in
wisol.cpp) receives the sensor data (
altitude) and aggregates them into a single Sigfox message:
To prevent too many messages from being sent over Sigfox, the Network Task includes a Throttle Feature to limit the sending of messages. So we send only what we need, when we need to.
The Network Task forwards the outgoing Sigfox message to the UART Task, which manages the Wisol module for transmitting Sigfox messages. Why create another task for UART?
How Do We Handle Wisol UART Commands?
The Wisol module communicates with Blue Pill via the UART port (a.k.a. Serial port) at the slow speed of 9600 bps. Normally the UART Task would have to send a character, wait a while, send another character, wait again, …. Then repeat the process for receiving characters.
But the Blue Pill is designed for multitasking! While sending or receiving characters, the Blue Pill could read some sensor data or compose the next Sigfox message. If you read the UART code in
uart.cpp, the UART Task optimises the available time by listening for Interrupts.
The UART Task is notified by the Blue Pill’s UART hardware — hence the “Interrupt” — whenever new characters are ready to be read. The UART Task is no longer busy waiting for data, it can now give up its waiting time to cocoOS, which will schedule another Sensor Task or Network Task to run (if any). The interrupt code is here:
The Wisol module accepts
AT commands for transmitting and receiving Sigfox messages — you can see examples here. The
AT commands are not composed in the UART Task, but rather in the Network Task. So that we may reuse the UART Task for other UART duties in future.
Need to learn more about the Network Task and UART Task? Check out this article.
Configure The Blue Pill Program
Before we run the program, there are some settings that we need to configure…
enable_debug(); // Uncomment to allow display
// of debug messages in development
// devices. NOTE: This will hang if
// no debugger is attached.// disable_debug(); // Uncomment to disable display
// of debug messages. For use in
// production devices.
1️⃣ Enable or Disable Debug Mode: By default the program runs in Debug Mode. Debugging messages are displayed on the Blue Pill console to let you know that the program is indeed running. However this requires the ST-Link to be connected. If the ST-Link is not connected, the Blue Pill’s Green LED (labelled
PC13) will blink at startup…
✳️ On — ◻️ Off — ✳️ On —— ◻️ Off — ◻️ Stays Off
And hangs there indefinitely waiting for the ST-Link (normally the LED should continue blinking). If you do not wish to use ST-Link for your production Blue Pill: Edit
main.cpp, comment out
enable_debug(), and uncomment
disable_debug() like this…
disable_debug(); // Debug is now disabled.
2️⃣ Set the Sigfox RCZ Region: Edit
main.cpp and look for this line of code…
// Start the Network Task.
setup_wisol(&wisolContext, &uartContext, uartTaskID,
COUNTRY_SG to your country code, e.g.
COUNTRY_US. This selects the frequency for Sigfox transmission.
3️⃣ Enable BME280 Simulator: If you have a SparkFun BME280 sensor, skip this step.
If you don’t have the BME280 sensor, you can configure the Blue Pill program to simulate a BME280 sensor and return hardcoded values for temperature, humidity and altitude. Edit
platform.h and uncomment all lines that define
SIMULATE_BME280. After editing, you should see this:
#define SIMULATE_BME280 // Uncomment to simulate a BME280 sensor
4️⃣ Enable Wisol Simulator: If you have a Wisol Sigfox Breakout Board, skip this step.
If you don’t have a Wisol Sigfox Breakout Board, you can simulate one in the Blue Pill program. Edit
platform.h and uncomment all lines that define
SIMULATE_WISOL. After editing, you should see this:
#define SIMULATE_WISOL // Uncomment to simulate a Wisol module
Build, Upload And Monitor Your Blue Pill Program
Connect the ST-Link (with Blue Pill) to your computer. Notice the buttons at the lower left? (See screen above) We’ll click them now. If the buttons are not visible, click the menu
Terminal → Run Task → PlatformIO… to run the commands instead.
► Click the ✅️
This compiles your Blue Pill program and links it with the
The build step produces a Blue Pill executable program.
► Click the ➡️
Our IDE connects to your Blue Pill via the ST-Link USB Debugger and writes the executable into the Flash Memory.
Your program will remain in the Flash Memory even after disconnecting the power. Just like the Arduino.
► Click in the menu:
Terminal → Run Task
Connect To STM32 Blue Pill to see the debug log (as displayed by OpenOCD). It works like the Arduino Serial Monitor.
When you’re done with the debug log, always click the 🗑️
Trash icon at the right.
This closes the Blue Pill connection so that you can continue uploading programs to the Blue Pill. Unfortunately the ❎️
Close icon doesn’t close the connection — it only hides the debug log, keeping the connection open. So always click the 🗑️
Watch Blue Pill Run
When the program runs on your Blue Pill, you will see signs of life when the LEDs start flashing like in the video above. The green LED at the top right (
PC13) flashes whenever the Network Task is aggregating some sensor data received from multiple Sensor Tasks. Even when you’re using a Simulated BME280 Sensor or Simulated Wisol Sigfox Module.
The video above shows the debug log for the Blue Pill program running with a real BME280 sensor and a real Wisol Sigfox module. Some highlights…
- Note that the sensor data collection never stops…
tmp >>for temperature,
hmd >>for humidity,
alt >>for altitude. Even when sending messages to Sigfox. That’s the power of multitasking on Blue Pill!
- Every message the program sends to Sigfox includes a Downlink Request. That means the Sigfox cloud will actually wait for our server callback URL to return an 8-byte response message that will be passed back to the device.
- Sigfox Downlink takes a long time to complete — up to 1 minute! That’s why we don’t see any acknowledgement of the sent message until 1 minute later. While waiting the program may still run other Sensor Tasks and the Network Task.
- Towards the end of the video we can see a successful Sigfox Downlink message received after 1 minute:
process_downlink_msg FEDCBA9876543210. We may insert our own code for Sigfox Downlink processing into
If you’re using a Simulated BME280 sensor or a Simulated Wisol Sigfox module, you’ll see hardcoded sensor data and Wisol commands. But the overall flow of the messages remains the same.
How does a Sensor Task read and send sensor data? What do the messages in the Debug Log mean? These are explained here, with links to the actual source code…
How does the Network Task receive, aggregate and transmit sensor data? That’s explained here…
You may see this error message in the Debug Log:
ERR_SFX_ERR_SEND_FRAME_WAIT_TIMEOUT. That’s because the Blue Pill is sending a Downlink Request to Sigfox and we haven’t configured your device for downlink yet. Let’s do that now…
Configure The Sigfox Backend
Follow the instructions provided by the makers of the Sigfox breakout board for activating the Wisol Sigfox module online. You’ll be guided through the steps to create a user account on the Sigfox Backend portal. (If you’re using a custom-built breakout board, see the screens below)
Let’s add a Sigfox callback to handle the downlink request. Log in to the Sigfox Backend:
Device Type, select your device type, click
New to create a Sigfox callback.
Use the settings below to configure the callback.
Body field, make sure there are no spaces at the end of each line.
For testing, you may use my Sigfox Downlink Server URL:
This Sigfox Downlink Server is hosted on my personal Amazon Cloud account and it has been hardcoded to return the downlink message
fedcba9876543210 for any device ID. I hope this helps to make your Sigfox Downlink development and testing easier.
After creating the callback, click the circle in the
Downlink column. It should show as a filled circle, not an empty circle.
Sigfox Downlink is now enabled for your Blue Pill!
Check the Blue Pill Debug Log in Visual Studio Code and confirm that your Blue Pill is still running.
Device → Messages to check the messages sent by your Blue Pill to Sigfox.
You’ll see two arrows in the
- The first arrow should show
Callback Status (OK)
- The second arrow should show
Downlink Status (Acked)
This information is useful for troubleshooting problems with our Downlink Server.
Still not receiving any messages? Sometimes the Sigfox Sequence Number may overflow for your device if your device has transmitted many messages while out of network coverage.
To fix this, go to
Device → Information and click
Disengage Sequence Number. Your device should be able to send messages to Sigfox now. The
Device → Events page may also give you clues why your device has stopped transmitting.
Unleash Your Blue Pill
You’re now all set to unleash your powerful new Blue Pill IoT gadget!
Remember to disable debug mode, as mentioned earlier. Otherwise your Blue Pill will stop flashing and wait forever to be connected to an ST-Link.
We have been using the ST-Link to power our Blue Pill. Consider getting a Breadboard Power Supply like the one shown at the top of the photo. Go to AliExpress and search for:
Breadboard Power Supply Module MB-102 Model 830
To build your own Sigfox Downlink Server for handling the callbacks, read the section “Our Downlink Server” in this article.
I have written a tutorial on connecting STM32 Blue Pill to a WiFi network via ESP8266…
Connect STM32 Blue Pill to ESP8266 with Apache Mynewt
Send sensor data to a CoAP server and perform WiFi Geolocation with ESP8266
And another tutorial on connecting Blue Pill to NB-IoT…
Connect STM32 Blue Pill to NB-IoT with Quectel BC95-G and Apache Mynewt
Build a real IoT sensor with STM32 Blue Pill and Quectel BC95-G Global NB-IoT module
What’s coming next? Since I teach IoT, please suggest which IoT topics I should write about!
I’m now creating a version of the Sigfox breakout board using the newer InnoComm SN10–12 Sigfox module. If I can resolve the InnoComm procurement issues with my PCB manufacturer (Seeed Shenzhen), I’ll definitely update this tutorial.
Breakout board for InnoComm Sigfox module SN10–12. Contribute to lupyuen/innocomm-sigfox-breakout development by…
I’m also extremely excited about the use of FPGAs for IoT. With FPGAs we could create highly power-efficient IoT devices. I had an amazing experience with the GOWIN FPGA, I’ll be using it soon to create more advanced IoT gadgets.
Would you be interested in a Chinese version of this article? Please let me know!
Blue Pill Tips: How To Solder Header Pins To Blue Pill
If you’re experienced in soldering, you can skip this section. But if you haven’t soldered anything before (like me before I started Blue Pill programming), I have some useful tips for beginners soldering the Blue Pill header pins.
The principles of soldering are explained here…
How to Solder: Through-Hole Soldering — learn.sparkfun.com
Soldering is one of the most fundamental skills needed to dabble in the world of electronics. The two go together like…
…but I found some steps difficult to execute properly. After some experimenting and tweaking, I found the right tools and techniques for beginners. Here’s what I’m using…
Soldering Iron with LEDs: Get a soldering iron with LEDs (so you can see what you’re soldering) and a tiny solder tip. I’m using the Flat Solder Tip that came with the soldering iron. Why Flat Tip and not Pointed Tip? Because a Flat Tip is easier to tap on header pins to heat them up (you’ll see in the video below).
SP15NUK | Weller SP15NUK 230V Electrical Soldering Iron, 15W, UK Plug | RS Components
Buy Weller SP15NUK 230V Electrical Soldering Iron, 15W, UK Plug SP15NUK or other soldering-irons online from RS for…
Fine Solder Wire (0.38 mm): I used a very fine solder wire, much finer than the normal ones. They are more “forgiving” if you make mistakes, because you’ll only need to fix the tiny solder dabs of mistakes that you have committed. Instead of big solder blobs that are harder to fix. But note that you will have to touch up the soldering for each pin to provide sufficient solder.
RS Pro 0.38mm Wire Lead solder, +183 → +188°C Melting Point | RS Components
Buy RS Pro 0.38mm Wire Lead solder, +183 → +188°C Melting Point or other solders online from RS for next day delivery…
Soldering Kit: Get a soldering stand with magnifying glass. Get a clamp to secure your Blue Pill before soldering. Mount your Blue Pill on a mini-breadboard before soldering. Don’t forget the sponge (the yellow thing in the photo above).
Ready to solder? Use the technique above to measure the header pins and break into two rows very gently.
Carefully align the header pins and mount the Blue Pill on a mini-breadboard. The header pins may become dislodged from the yellow sockets if you rock them back and forth while mounting. To prevent this, use a hard flat non-conductive surface (like my USB hub above) to press down firmly and slowly on the pins.
The Blue Pill may wobble as you solder — stabilise it temporarily with Blu-Tack before soldering. There should be no wobbly parts during soldering.
Secure the mini-breadboard to the soldering clamp. Again, use Blu-Tack to fix any wobbly parts.
Power on the soldering iron and wait for it to heat up. To solder each pin:
- Don’t tap the soldering iron on any pins yet. Keep the tip away from any part of the Blue Pill.
- Straighten the solder wire.
- Tap the solder wire on the soldering iron so that it starts melting (the shiny blob in the video below).
- Gently tap the soldering icon on the pin to heat it up. Don’t leave it there for more than a few seconds because you may damage the components connected to the pin. Lift the soldering iron and tap again if necessary.
- Push the solder wire towards the space between the pin and the metal ring. If the pin is hot enough, the solder should melt and fill the space.
- Repeat the steps until the metal ring is totally covered by solder. Remember: Don’t rest the soldering iron tip on any of the pins for more than a few seconds.
- Rotate the clamp to solder the pins on the other side. Always point the soldering iron tip away from any parts mounted on the Blue Pill.
- If your hands are shaky, rest them on the soldering clamp while soldering.
Watch the video below a few times and you’ll understand what I mean. This technique is slower because of our fine solder wire, but it works better for older people like me with shaky hands and poor eyesight.
The complete source code for this article is available here…
IoT program for Arduino Uno / STM32 Blue Pill (libopencm3) that reads BME280 temperature + humidity + altitude sensors…
I got started on Blue Pill programming with this great “Beginning STM32” book by Warren Gay (possibly the only book published on Blue Pill)…
Beginning STM32 - Developing with FreeRTOS, libopencm3 and GCC | Warren Gay | Apress
This book will help you develop multi-tasking applications that go beyond Arduino norms using FreeRTOS and…
Later as I started digging for more details (like the “Half-Done Interrupt”) the “Mastering STM32” book was valuable. Note that it talks about the entire family of STM32 microcontrollers, and it uses the official STM32 API, not
libopencm3. So it might overwhelm you…
With more than 600 microcontrollers, STM32 is probably the most complete ARM Cortex-M platform on the market. This book…
The Blue Pill (STM32F103C8) Datasheet and other official docs are here…
STM32F103C8 - Mainstream Performance line, ARM Cortex-M3 MCU with 64 Kbytes Flash, 72 MHz CPU…
STM32F103C8 - Mainstream Performance line, ARM Cortex-M3 MCU with 64 Kbytes Flash, 72 MHz CPU, motor control, USB and…
And the “The Insider’s Guide To The STM32 ARM®Based Microcontroller” is a terrific intro to the STM32 family…