I needed a simple MQTT client for my embedded projects. I know that there are already many implementations available, but I wanted to learn also the protocol internals so I ended up in writing it from scratch (MQTT protocol is pretty well documented and the specification is available from mqtt.org). Continue reading “Potato Bus MQTT”
Just about every summer I have been thinking about building a sensor, which measures water temperature from the lake at our summer cottage. So I would need a board with few gpio ports to connect a DS1820 sensor and some radio communications to send data to my database server. As I already have Wifi access point installed it would nice be able to use it directly.
When I was researching for suitable parts for the system, I bumped into small module called EMW3162. The module has a STM32 Cortex-M3 microcontroller and
Broadcom Cypress Wiced-compatible Wifi chip. The module costs less than $10 at Seeedstudio.com – more than popular ESP8266, but STM32 cpu has more memory and peripherals. For first module, a ~$20 development board is needed (either EMB-380-S2 or EMB-WICED-S).
To program the system, there are two alternatives: SDK provided by module maker MXCHIP and Wiced SDK provided by Broadcom. I ended experimenting with Wiced SDK, as Broadcom provides it for free (registration required, however) along with nice support community. SDK needs some patching for EMW3162, but required changes are available from github.
Wiced SDK provides multiple choices for network stack and RTOS. I ended trying FreeRTOS + LwIP combination, mostly those components being open source. Examples seem to work OK, so it is pretty easy to get things up and running.
But I have always been using Pico]OS for my embedded hobby projects. As Wiced SDK has clean api to add support for any RTOS, I couldn’t resist to start writing such layer for Pico]OS. It was actually quite easy task, all that was needed were ~15 functions to wrap Pico]OS services (threads, semaphores and queues mainly).
Pico]OS approach to building embedded systems is a little bit different than Wiced SDK, however. Wiced SDK seems like a one-stop service for about everything you’ll need to build a Wifi-enabled embedded system: it contains network stack, rtos and API functions for GPIO, ADC etc. Pico]OS on the contrary has quite powerful Makefile system which makes it easy to build separate module libraries for different needs.
I wanted to build a Pico]OS library module containing LwIP driver which I could use with existing picoos-lwip library (it uses currently HEAD revision from LwIP project). Luckily, Wiced SDK is pretty well organized and it was quite easy to find out which files I would need to compile for complete driver. There are rougly two layers in SDK: “WICED” – the full SDM and “WWD” – driver layer. I needed mostly files from WWD-layer only.
WICED SDK and Pico]OS have overlapping functionality when it comes to console serial port output/input. I wanted to use Pico]OS stuff also here, because I have a quite complete newlib syscall support layer in picoos-micro library, allowing me to use standard C stuff to print log messages and read/write files. I couldn’t find a way to fully disable USART support in WICED, so I ended up in patching SDK sources for that part.
Another, equally working approach would have been to disable console input/output api from Pico]OS nano layer and use it from Wiced SDK.
Wifi chip needs firmware before it actually works. I solved this a little bit differently than in Wiced SDK by putting the firmware file into filesystem (/firmware/CHIPNAME.bin) and serving it from there using pretty much standard C stuff.
I can now continue with my lake temperature sensor development, hopefully getting something up and running for next summer.
Picoos-net networking library has been updated to use filesystem API layer from picoos-micro library. This gives unified uosFileRead/uosFileWrite/uosFileClose methods to access socket connections in similar manner as files.
On platforms that use newlib runtime (Cortex-M) it is also possible to read/write sockets using standard C functions through newlib syscalls.
Change is not backward compatible, NetSock* handles must be replaced by UosFile* handles in applications.
I have been using two different approaches to store files in my embedded projects. First is the excellent FatFs module from elm-chan.org, second is a simple solution for read-only files using file2c-generated string tables in flash memory.
Although both these solutions work OK for code that I have written myself, the non-standard API is a problem if I would like to integrate code from other projects. Third-party code typically relies on stdio or unix-style API for file access. My solution to this was to write a slim uosFile -layer, which provides:
- Simple API that can be wrapped into newlib system calls
- File descriptor management for various modules
- Support for multiple, different file systems in same system mounted at directories I want
- Routing of API calls to file system modules based on mount point.
API contains functions like uosFileOpen, uosFileClose & uosFileRead. On platforms that use newlib as runtime library (like Arm environments for example), these are used inside _open, _close & _read system calls so they are usable from standard stdio functions. Platforms that use something else than newlib might required different steps to get the big picture working.
Library tries to be modular. Calls between layers are mostly done via structures containing C function pointers, which should make it easy to add for example new file systems: just provide a mount function and UosFile_I & UosFS_I structures. Same idea applies also to disk layer.
As most filesystem implementations require some kind of system to manage structures related to open files, library offers “bittab” structure with some related API calls & macros. A “bittab” is just a struct array of given size, but it contains also a bitmap table. Each bit in bitmap table tells if it’s associated slot in struct array is allocated or not. Access to bitmap is protected by mutex, so it is safe to use this also with multiple active tasks.
There is also a simple layer for using MMC/SD cards with Fat FS. The code is based on examples that are available from same elm-chan.org site as Fat FS itself. To use this layer, application needs to provide SPI methods for the chip that is being used. This is done by providing a UosMmcDisk structure with correct values in UosMmcSpi_I function pointers and calling uosAddDisk to register it. An example for such setup can be found in my python-test project (see test.c and mmcspi.c).
Reference manual for library is available here.
When I started toying with microcontrollers several years ago, I kind of ignored Microchip’s PIC family completely. I think it was 8-bit stuff only those days. Although having some history with 8-bit Z80 in my early years, my real job with 32/64-bit unix servers made me look for something “bigger”, which lead me to the LPC2000 series from Philips (NXP today).
But when NPX released some Arm Cortex-M0 chips in hobbyist-friendly DIP packages they made me look around what else might be available in similar packages. I knew about PIC32MX family from Microchip before, but wasn’t really interested in it, because I thought that Arm Cortex-M stuff would dominate the world (maybe it will, maybe not). But breadboarding is really nice during prototyping and PIC32MX chips in DIP packages have much more flash and ram than those offered by NXP. Continue reading “Pic32 port for Pico]OS”