📚 CMPE2250: Lesson — Analog-to-Digital Conversion on STM32G0
🎯 Learning Objectives
By the end of this lesson, students will be able to:
-
Explain what an ADC does and why embedded systems need it.
-
Describe the STM32G0 ADC architecture: resolution, sampling time, channels, and clocking.
-
Configure the ADC in single‑conversion and continuous modes.
-
Trigger conversions using software and timers.
-
Read conversion results using polling, interrupts, and possibly DMA.
-
Validate ADC behavior using a multimeter, waveform generator, and logic analyzer (for triggers).
1️⃣ Why ADC Matters in Embedded Systems
Embedded systems interact with the real world, which is inherently analog. Sensors such as:
-
Temperature (NTC, thermistors)
-
Light (LDR, photodiodes)
-
Position (potentiometers)
-
Pressure, force, sound
All output voltages that must be digitized before the MCU can process them.
The ADC bridges this gap by converting an input voltage $V_{in}$ into a digital number:
\[\mathrm{Digital\ Value}=\frac{V_{in}}{V_{ref}}\times (2^N-1)\]Where N is the resolution (12 bits on STM32G0).
2️⃣ STM32G0 ADC Architecture (G0B1RE‑specific)
Key Features
-
12‑bit ADC
-
Up to 19 channels (GPIO + internal: Vrefint, temperature sensor)
-
Configurable sampling time (affects accuracy vs. speed)
-
Hardware oversampling
-
Single, continuous, scan, and discontinuous modes
-
DMA support
-
Hardware triggers (TIM1, TIM3, TIM6, EXTI, etc.)
Conceptual Diagram (Mermaid)
flowchart LR
A[Analog Input Pin] --> B[Sample & Hold]
B --> C[SAR Conversion Engine]
C --> D[12-bit Result Register ADC_DR]
D -->|optional| E[DMA Controller]
D -->|optional| F[Interrupt Handler]
3️⃣ Clocking and Calibration
ADC Clock Sources
-
System clock (SYSCLK)
-
PLL outputs
-
Asynchronous clock
For beginners, use the synchronous clock derived from the system clock.
Calibration
The STM32G0 ADC must be calibrated before first use:
-
Enable ADC clock.
-
Ensure ADC is disabled.
-
Start calibration.
-
Wait for calibration to finish.
-
Enable ADC.
This is a common pitfall — conversions silently fail if calibration is skipped.
4️⃣ Registers We Must Know
| Register | Purpose |
|---|---|
| ADC_ISR | Status flags: EOC (end of conversion), EOS (end of sequence), OVR, ADRDY |
| ADC_IER | Interrupt enables for EOC, EOS, OVR, ADRDY |
| ADC_CR | Main control: ADEN, ADDIS, ADSTART, ADCAL |
| ADC_CFGR1 | Resolution, data alignment, continuous mode, DMA enable, trigger config |
| ADC_SMPR | Sampling time selection |
| ADC_CHSELR | Channel selection (bitmask of active channels) |
| ADC_DR | Data register containing the 12‑bit conversion result |
5️⃣ Minimal Working Example (Single Conversion, Polling)
- Minimal bare-metal flow to read a single channel (e.g.,
PA0 = ADC_IN0):
// Enable clock
RCC->APBENR2 |= RCC_APBENR2_ADCEN;
// Calibration
ADC1->CR &= ~ADC_CR_ADEN;
ADC1->CR |= ADC_CR_ADCAL;
while (ADC1->CR & ADC_CR_ADCAL);
// Enable ADC
ADC1->CR |= ADC_CR_ADEN;
while (!(ADC1->ISR & ADC_ISR_ADRDY));
// Select channel (e.g., PA0 = ADC_IN0)
ADC1->CHSELR = ADC_CHSELR_CHSEL0;
// Start conversion
ADC1->CR |= ADC_CR_ADSTART;
// Wait for end of conversion
while (!(ADC1->ISR & ADC_ISR_EOC));
// Read result
uint16_t value = ADC1->DR;
6️⃣ Adding Continuous Mode + DMA (for smoother signals)
Why DMA?
-
Avoids CPU polling
-
Enables high‑rate sampling
-
Perfect for labs involving waveform capture or filtering
Workflow
-
Configure ADC in continuous mode.
-
Enable DMA in ADC_CFGR1.
-
Configure DMA channel (peripheral → memory).
-
Start ADC.
-
DMA fills a circular buffer.
7️⃣ Hardware Triggering (Timer‑Driven Sampling)
ADC sampling frequency is not “automatic” — it must be controlled.
Example: TIM3 → ADC Trigger
-
Configure
TIM3to generateTRGOat a fixed rate. -
Set ADC external trigger source to
TIM3_TRGO. -
ADC samples at exactly the timer frequency. This is a great lab for teaching deterministic sampling.
8️⃣ Validation Strategy
Students should verify:
-
ADC reading matches expected voltage Use a multimeter on the analog pin.
-
Sampling frequency is correct
-
Use a scope on the timer trigger pin.
-
DMA buffer updates continuously
-
Print buffer indices or use a debugger watch window.
-
Noise behavior
-
Show how oversampling reduces jitter.