Posts

Microcontroller as Raspberry Pi peripheral

Image
Raspberry Pi Peripheral Sometimes you just need a real-time MCU to control an operation, but you want the full-blown OS capabilities of an MPU as well. There are many ways to handle this situation, but the one I want to discuss here is implementing a slave I2C interface in an MCU which you can use from a Raspberry Pi. Register Access Control of many peripherals involves manipulating and reading registers. Since this is a commonly understood approach, I will show you how to set up register access to your peripheral over I2C.  For your peripheral to be useful, the registers have to be planned out in terms of what functions they trigger and what data they present. That part will be up to you. To standardize and simplify the layout, the approach I present will use 32-bit registers laid out in a simple array, and any individual register can be one of: A read-only register whose value can't be changed from the Pi, A simple write register which can be changed by the Pi but doesn't tri...

Experiment: Queued Approach to I2C Device Driver

A Queued I2C Driver? There has been a large push at the PC & Server level lately for breaking software into small, container-based independent parcels. But container infrastructure for embedded computing is still in its infancy. So how can we improve software design methods for embedded computing using the tools we have available? I've always liked the simplicity and separation provided by message queues. One of the key benefits, to me, is the inherent synchronization - basing a software design around queues relieves a lot of concurrency problems and typically single-threads your access to critical resources. So I'm considering the idea of basing an I2C interface around a queue mechanism. An I2C part needing a software driver, say a real-time-clock, would implement the driver to do a register read by sending a queue message and waiting for a response. The firmware would initialize command and response queues, and start an I2C operations thread. Pros and Cons Before we discu...

Basic Scan-Mode A/D DMA (STM32H743)

Image
A/D in Scan Mode using DMA Overview I wanted to setup a simple scan-mode DMA on my STM32H743ZI2 Nucleo, for a v-drum project where I want to sample about 6 different analog inputs at 10 KHz. It turns out it is pretty easy to setup, but there are a few pitfalls I ran into that can save you considerable headache. Project Setup Start with a new project in CubeMX based on the H743ZI2 Nucleo. I choose not to initialize all peripherals, and just add the ones I want, which seems simpler. I am using CubeIDE 1.5.1. Some basic setup: In System Core / CORTEX_M7, enable the Prefetch and Caches  In Connectivity, set USART3 to Asynchronous mode.  By default it connects to PD8 and PD9, which sets up a serial connection via the ST-Link USB debug port.  The default baud rate is 115200. Then setup clocking: In the Clock Configuration tab, set PLL Source to HSI and set DIVM1 to /8 and DIVN1 to 120 and leave DIVP1 at /2.  Set the HPRE Prescaler to /2 and set the DxPREn dividers for the ...

FFT Analysis using CMSIS DSP Library

Image
FFT Analysis Many times, once you've captured a data stream from A/D or some other means, the next question is what is the frequency content of it? Generally, that means you have to use a Fast Fourier Transform to view the signal data in the frequency domain. There's a lot to signal analysis that I'm not going into here.  For a better coverage of that, I recommand LabKitty . This blog is just going to walk through the basic steps and some of the pitfalls of using an FFT in the real world. Setup I have an ST Micro STM32F746G Discovery board. The processor is an ARM Cortex-M7 with a vector processing unit, and the ARM powers have conveniently provided an optimized DSP library as part of CMSIS . The Discovery board has a TFT LCD (480 x 272) which I will use to display the output of the FFT in graphical form. Otherwise I'm just using the microcontroller itself to sample the data and process it, not even using the external RAM available on the Discovery. Sampling Data In a n...

Customizing the ADC Sample Rate

Image
So in the last post I talked about getting streaming data from an Analog/Digital Converter unit on the STM32F746. In that case I let the ADC run at a pretty high clock rate, based on the PCLK2 configuration and a single ADC prescaler.  Needless to say, the options for sample rate are pretty limited, even when you throw in the 8-setting "per-channel" delay option. So, what if you want to sample at a more arbitrary rate, or even change the sample rate after booting? One way is to switch from "Continuous" mode to triggered mode. Timer Triggered ADC So if you look closely at the ADC settings in CubeMX, you will see the "External Trigger Conversion Source" under the ADC_Regular_ConversionMode section. This allows you to specify a timer event that will initiate a conversion.  For this mode, we want to disable the Continuous mode of the ADC, leaving it in single conversion mode, so that each trigger event starts a single conversion. How Does It Work With DMA? Wh...

Double-Buffered DMA from ADC

Image
Analog Streaming Data Capture Overview If you want to do high-powered Analog to Digital Conversion in a microcontroller, the best way is to use two buffers and cycle between them, so you can be recording data into one buffer and processing the data already in the other buffer.  ST-micro's STM32F7 products, and others, make this possible. While the API functions are available to do this, as of this writing it isn't all packaged together so you can do it easily. Here is what I found when I went through the process. The STM32F746G Discovery board is capable of taking ADC samples at more than 1 million per second, so it could be useful as a low-bandwidth scope, and audio spectrum analyzer, and so on. Project Setup To sample ADC in streaming mode, start with a CubeMX project based on the Discovery board. I choose not to initialize all peripherals, and just add the ones I want, which seems simpler. I am using CubeIDE 1.5.1. Some basic setup: In System Core / CORTEX_M7, enable the Pre...