2026-03-24 6:22 PM
Hi all,
I'm trying to create a project to read a temperature sound like a DS18B20. The problem is that I need a precise and stable delay time. Using Systick isn't possible because there's a conflict when using BLE. I tried using an MFT, but I can't create a function to vary the delay. I based my approach on a timer in MFT_Mode1 and a prescaler 80-1 on the 16MHz oscillator.
static inline void delay_us(uint32_t us) {
uint32_t ticks = us / 10; // 1 tick ≈ 10 µs
if (ticks == 0) ticks = 1;
uint16_t start = MFT_GetCounter2(MFT1);
while ((uint16_t)(MFT_GetCounter2(MFT1) - start) < ticks) {
}
}
static void MFT1_Reset(void) {
MFT_SetCounter2(MFT1,0);
}
static uint16_t MFT1_Get(void) {
return MFT_GetCounter2(MFT1);
Even if I vary my e.g. delay_us(2500) , I still get pulses at 10µs.
For test in loop
/* Start MFT timers */
MFT_Cmd(MFT1, ENABLE);
while (1) {
GPIO_SetBits(GPIO_Pin_6);
delay_us(250000); // 250 ms
GPIO_ResetBits(GPIO_Pin_6);
delay_us(250000);
}Thank for help
2026-03-25 2:01 AM - edited 2026-03-25 2:02 AM
Main issues:
(uint16_t)(MFT_GetCounter2(MFT1) - start)can never grow beyond that period, so the delay function will always return after ~10 µs, no matter what us you pass.What to do:
mftInit.MFT_Prescaler = 16-1 ; // 16MHz/16 = 1MHz -> 1 µs per tick
mftInit.MFT_Period = 0xFFFF; // free-runningCorrect delay_us
Since the counter is 16-bit, you can measure directly up to a maximum of about 65ms at a time. For longer delays (e.g. 250ms), you do:
static inline void delay_us(uint32_t us)
{
if (us == 0) return;
uint16_t start = MFT_GetCounter2(MFT1);
while ((uint16_t)(MFT_GetCounter2(MFT1) - start) < (uint16_t)us) { }
}
void delay_us_blocking(uint32_t us)
{
while (us > 60000)
{
delay_us(60000);
us -= 60000;
}
if (us) delay_us(us);
}
Test (different calls at lines 6 and 8):
MFT_Cmd(MFT1, ENABLE);
while (1)
{
GPIO_SetBits(GPIO_Pin_6);
delay_us_blocking(250000); // ~250ms
GPIO_ResetBits(GPIO_Pin_6);
delay_us_blocking(250000); // ~250ms
}Hope that helps?
Regards
/Peter
2026-03-25 2:07 AM
2026-04-02 4:43 AM
You might also look at synthesising the timing using UART or SPI - Analog Devices have an App Note on that...
eg, see: Dallas (sic) iButton and UART