2019-11-19 08:42 AM
my data for this looks like the following without giving input
PA0 PA1 PA4 PA5
0 250 216 190
I expect this
PA0 PA1 PA4 PA5
0 0 0 0
and when i start giving channel PA0 data with a sensor all my channels are changing like so
PA0 PA1 PA4 PA5
400 350 290 220
PA0 should be the only one significantly changing but it interferes with the other channels data
Here is how im printing the data
uint16_t adc_dma_buffer[4];
while(1)
{
uint16_t fsr1_data = adc_dma_buffer[0];
uint16_t fsr2_data = adc_dma_buffer[1];
uint16_t fsr3_data = adc_dma_buffer[2];
uint16_t fsr4_data = adc_dma_buffer[3];
// Do every 1s
char buffer[100];
// Print ADC conversion results
sprintf(buffer, "%d\t %d\t %d\t %d\r\n", fsr1_data, fsr2_data, fsr3_data, fsr4_data);
putty_print("FSR number: ");
putty_print(buffer);
}
Here is my code for the ADC and DMA
#include "FSRs.h"
#include "stm32f0xx_hal.h"
#include "GPIOs.h"
void FSRs_init() {
// SETTING UP THE PINS
// Enable GPIOA clock
RCC->AHBENR |= RCC_AHBENR_GPIOAEN;
// Configure pin PA0, PA1, PA4 PA5 as analog
GPIOA->MODER &= ~(GPIO_MODER_MODER0 | GPIO_MODER_MODER1 | GPIO_MODER_MODER4 | GPIO_MODER_MODER5);
GPIOA->MODER |= GPIO_MODER_MODER0 | GPIO_MODER_MODER1 | GPIO_MODER_MODER4 | GPIO_MODER_MODER5;
// SETTING UP ADC
// Enable ADC clock
RCC->APB2ENR |= RCC_APB2ENR_ADC1EN;
// Reset ADC configuration
ADC1->CR = 0;
ADC1->CFGR1 = 0;
ADC1->CFGR2 = 0;
ADC1->CHSELR = 0;
// Enable continuous conversion mode
ADC1->CFGR1 |= ADC_CFGR1_CONT;
// 12-bit resolution
ADC1->CFGR1 &= ~ ADC_CFGR1_RES;
// Select PCLK/2 as ADC clock
ADC1->CFGR2 |= ADC_CFGR2_CKMODE_1;
// Set sampling time to 28.5 ADC clock cycles
ADC1->SMPR = 0x03;
// Select channel 0, 1, 4, 5
ADC1->CHSELR |= ADC_CHSELR_CHSEL0 | ADC_CHSELR_CHSEL1 | ADC_CHSELR_CHSEL4 | ADC_CHSELR_CHSEL5;
// SETTING UP DMA
// Start DMA clock
RCC->AHBENR |= RCC_AHBENR_DMA1EN;
// Peripheral is ADC1 DR
DMA1_Channel1->CPAR = (uint32_t)&ADC1->DR;
// Memory is adc_dma_buffer
DMA1_Channel1->CMAR = (uint32_t)adc_dma_buffer;
// Set Memory Buffer size
DMA1_Channel1->CNDTR = 4;
// Reset DMA1 Channel 1 configuration
DMA1_Channel1->CCR = 0x00000000;
// Configure DMA1 Channel 1
// Peripheral -> Memory
// Peripheral is 16-bit, no increment
// Memory is 16-bit, increment
// Circular mode
DMA1_Channel1->CCR |= DMA_CCR_MSIZE_0 | DMA_CCR_PSIZE_0 | DMA_CCR_MINC | DMA_CCR_CIRC;
// Enable DMA1 Channel 1
DMA1_Channel1->CCR |= DMA_CCR_EN;
/* (1) Ensure that ADEN = 0 */
/* (2) Clear ADEN by setting ADDIS*/
/* (3) Clear DMAEN */
/* (4) Launch the calibration by setting ADCAL */
/* (5) Wait until ADCAL=0 */
if ((ADC1->CR & ADC_CR_ADEN) != 0) /* (1) */
{
ADC1->CR |= ADC_CR_ADDIS; /* (2) */
}
while ((ADC1->CR & ADC_CR_ADEN) != 0)
{
/* For robust implementation, add here time-out management */
}
ADC1->CFGR1 &= ~ADC_CFGR1_DMAEN; /* (3) */
ADC1->CR |= ADC_CR_ADCAL; /* (4) */
while ((ADC1->CR & ADC_CR_ADCAL) != 0) /* (5) */
{
/* For robust implementation, add here time-out management */
}
// START ADC
// Enable ADC DMA Request in circular mode
ADC1->CFGR1 |= ADC_CFGR1_DMACFG | ADC_CFGR1_DMAEN;
// Enable ADC
ADC1->CR |= ADC_CR_ADEN;
// Start conversion
ADC1->CR |= ADC_CR_ADSTART;
}
2019-11-20 07:27 AM
Are the ADC inputs fed from low-impedance sources? Show us schematics.
JW
PS. Change your username to a normal nick.
2019-11-21 10:03 AM
Each pin is connected to a force sensor and about 3.3 volts. The force sensor is:
Resistors Force Sensing Standard Round Format Connector Housing
Manufacturer #: FSR03CE
Allied Stock #: 71202270
and the specs and features of it are as follows:
Series Features:
Small, thin and light
Largely immune to EMI and water events
Low power
False touch rejection
Cost effective
Highly Durable (>10M activations typical)
Long term drift 1kg for 48hrs, Per log time < 2%
Single part repeatability 100 actuations of 1kg, 1 standard deviation/mean 5%
Part to part repeatability 100 sensors same batch, 1 std. deviation/mean ±10%
Low temp. storage –20°C for 250hrs, Avg. change in resistance of 5 Sensors 2%
High temp. storage +85°C for 250hrs, Avg. change in resistance of 5 Sensors 9%
High humidity storage +85°C/85%RH for 250hrs, Avg. change in resistance of 5 sensors 10%
Lifecycle durability (10M) 1kg force at 3Hz, Avg. change in resistance of 4 sensors 4%
Hysteresis 100 actuations of 1kg, Avg. change in resistance of 100 samples 5%
Operational temp. range 100 cycles at 0.5kg, –20 to +60°C
Linear resistance Resistance between pins 1 & 2, Average of 100 parts same batch:
— FSP01CE: 1.25k, ±15%
— FSP02CE: 0.76k, ±15%
— FSP03CE: ±15%
2019-11-21 10:28 AM
OK, those are basically variable resistors. How exactly do you have them electrically connected to the ADC inputs?
JW
2019-11-23 10:48 AM
they are all connected to a 3.3 volt line from the STM itself
2019-11-23 10:56 AM
I also found this thread as well, that i think would be useful but the Links given are dead and unhelpful. is there a template showing multiple channels of the ADC using a DMA?
https://community.st.com/s/question/0D50X00009Xkgn8/stm32f072-adc-and-dma-help
2019-11-24 02:08 AM
You can't measure resistance by connecting resistors one end to VCC and other to ADC input. You'd need to put it as part of a voltage divider and condition the output by an amplifier.
JW