Skip to main content

First steps with ESP32 (M5Stack BASIC Kit)

Hello World

I have a micro-controller project idea that requires the following:

  • LCD screen
  • Buttons
  • Bluetooth LE
  • USB (for a dongle)
I've had good experience with the ESP8266 (specifically the Wemos D1 Mini) and thought I would try an ESP32. I discovered the M5Stack product range which is quite handy as it goes beyond barebones in its form factor, so I purchased an M5Stack BASIC Kit as well as an M5Stack USB Module.

My preferred language/programming environment is Arduino with PlatformIO as the IDE. I use Windows 10 and run PlatformIO in Visual Studio Code, so the first step is to download a Windows CP2104 driver for programming the M5Stack device (referred to as the M5Core). This is provided on the Arduino IDE Development page of the M5Stack website (I am only using that page for the driver as I don't intend to use the Arduino IDE).

The Windows driver can also be used with M5Stack's EasyLoader software which is provided for test purposes. It's necessary to hit the RESET button on the device to start the download after the Connecting... message appears in the software. This is a good way to verify that the device can be programmed and which COM port has been selected.

The M5Stack GitHub site hosts some basic examples, so I'm going to try the HelloWorld one!

M5Stack Core ESP32 is available as a board type in PlatformIO (having installed the latest Arduino framework). A straight build of the HelloWorld code will give the following message fatal error: M5Stack.h: No such file or directory. This is because a library is also required for the device. So I installed the M5Stack by Zibin, M5Stack library.

Once the library is installed, it's possible to build and upload the code. The COM port is auto-detected in my case, and it's necessary to use the RESET button to initiate the upload. I have found the RESET button quite erratic (it doesn't always want to start the upload), but in any case my preference is to enable remote OTA uploads which should avoid this issue in the first place. Note that the device seems to need a further press on RESET to wake it up following an upload.

For those having upload issues, there is a useful thread on GitHub, with the following suggestions which both seemed to help me:
  • Change the baud rate (upload_speed = 115200 in the platformio.ini file)
  • Press and hold the RESET button for 6 seconds, then start the upload and release the RESET
As an aside, there is a forum thread here describing how to force reset a device using RESET in conjunction with button A.

OTA programming

There are two ways to do the OTA on ESP32, either basic or web updater. I am interested in the basic method as I will be uploading directly from PlatformIO.

It's necessary to use extra code in each program requiring the OTA facility, and there is a generic example for ESP32 on GitHub.

Before starting on the OTA, I'm going to test that I can get serial messages back to PlatformIO for debugging purposes. This is necessary to find out the IP address assigned to the device.

I've added the following lines to main.cpp of the Hello World example:

    Serial.begin(115200);
    Serial.println();
    Serial.println("Hello World over serial");

I then tested this with an Upload and Monitor command from PlatformIO. It was necessary to press RESET after the upload to power on and then the monitor gave garbage because it was set to 9800 baud.

After changing the monitor baud rate (monitor_speed = 115200 in the platformio.ini file), the serial message was received correctly (following some diagnostic messages).

I then used the code from the GitHub OTA example and edited it to use my local WiFi credentials. The program ran successfully and the PlatformIO terminal displayed the IP address in use for the OTA service.

I then commented out the upload speed in the platformio.ini file and added the upload port and protocol (where the IP address is that given in the terminal):

monitor_speed = 115200
; upload_speed = 115200
upload_protocol = espota
upload_port = 192.168.0.182

At this point, the code is not writing anything to the LCD display, so as a minimum I am going to write the IP address there using code from the Hello World example.

I discovered that the M5.begin() function writes a message out on the serial channel (M5Stack initializing...OK) so that function should be called after the normal serial channel initialisation (also called early in the setup function because otherwise the terminal output gets corrupted):

  Serial.begin(115200);

  // Initialize the M5Stack object and power
  M5.begin();
  M5.Power.begin();

Then at the end of the setup function, write to the LCD after the normal serial write (with an enhanced text size):

  Serial.println(WiFi.localIP());

  // LCD display
  M5.Lcd.setTextSize(2);
  M5.Lcd.print(WiFi.localIP());

I've arrived at a working OTA example which makes remote programming straightforward but also any kind of programming easier due to the fiddly nature of the physical resets required during USB programming.

Comments

Popular posts from this blog

Amazon Dash Button with Node-RED built-in nodes

I bought an Amazon Dash button for experimentation (July 2017, in the UK). The part number I received was JK29LP (with FCC ID 2AETK-1013) which apparently is revision 2 of the hardware. There is a teardown here . There are at least a couple of Node-RED nodes published but they both have dependencies which I wanted to avoid: node-red-contrib-mydash requires tcpdump node-red-contrib-amazondash requires libpcap There is also a description here of a ping method but I did wonder if I could do it an alternative way without using the ping (which has its own complications due to needing root permissions on certain systems). I configured the button using the Amazon app as far as the wireless SSID and password, and on a button press I could see the button appearing in my router Attached Devices table (DHCP address reservation). It only takes a short lease so it would appear and then disappear in the router table. This gave me a MAC address (and also an IP address but I would not need