2022-01-19 08:16 AM
Hi everyone,
I'm dealing with some difficult problem for quite a while. I am using an stm32f411ce running on 80mhz. I have a code in which I am reading data from some sensors and then processing it. when I run the code it crashes randomly with different error calls. the processing code itself is proven to not be the problem, I have tested it on my pc with VScode. Here is my main setup and I2C setup. Thus this is the only code other then the processing it must be the problem.
The clock and simple pinout setup:
// set the HSEON bit high
RCC ->CR |= RCC_CR_HSEON;
//wait for the HSE to be ready
while (!(RCC ->CR & (1<<17)));
//while (!(RCC->CR & (1<<17)));
//set up the power registers
RCC ->APB1ENR |= RCC_APB1ENR_PWREN;
RCC ->AHB1ENR |= RCC_AHB1ENR_GPIOBEN;
PWR->CR |= (3<<14);
FLASH->ACR = (1<<8) | (1<<9)| (1<<10)| (2<<0);
uint32_t temp = FLASH ->ACR; //it is recommended to read the register
//FLASH->ACR = (1<<8) | (1<<9)| (1<<10);
RCC->AHB1ENR |= (1 << 1);
GPIOB ->MODER |= GPIO_MODER_MODE2_0; //Generel prupose output mode
GPIOB ->MODER &= ~GPIO_MODER_MODE2_1;
GPIOB ->MODER |= GPIO_MODER_MODE13_0; //Generel prupose output mode
GPIOB ->MODER &= ~GPIO_MODER_MODE13_1;
GPIOB ->MODER |= GPIO_MODER_MODE14_0; //Generel prupose output mode
GPIOB ->MODER &= ~GPIO_MODER_MODE14_1;
GPIOB ->MODER |= GPIO_MODER_MODE15_0; //Generel prupose output mode
GPIOB ->MODER &= ~GPIO_MODER_MODE15_1;
//OTYPER:
//0: Output push_pull (reset state)
//1: Output open-drain
GPIOB ->OTYPER &= ~(GPIO_OTYPER_OT_2); //push_pull
GPIOB ->OTYPER &= ~(GPIO_OTYPER_OT_13); //push_pull
GPIOB ->OTYPER &= ~(GPIO_OTYPER_OT_14); //push_pull
GPIOB ->OTYPER &= ~(GPIO_OTYPER_OT_15); //push_pull
//OSPEEDR:
//x0: Low speed
//01: Medium speed
//11: High speed
GPIOB ->OSPEEDR |= (3 << 4);
GPIOB ->OSPEEDR |= GPIO_OSPEEDER_OSPEEDR13;
GPIOB ->OSPEEDR |= GPIO_OSPEEDER_OSPEEDR14;
GPIOB ->OSPEEDR |= GPIO_OSPEEDER_OSPEEDR15;
//PUPDR:
//00: No pull-up, pull-down
//01: Pull-up
//10: Pull-down
//11: Reserved
GPIOB ->PUPDR &= ~(GPIO_PUPDR_PUPD2); //No pull-up, pull-down
GPIOB ->PUPDR &= ~(GPIO_PUPDR_PUPD13); //No pull-up, pull-down
GPIOB ->PUPDR &= ~(GPIO_PUPDR_PUPD14); //No pull-up, pull-down
GPIOB ->PUPDR &= ~(GPIO_PUPDR_PUPD15); //No pull-up, pull-down
//set the pll scalers
RCC ->PLLCFGR &= ~(63 << 0); // PLLM div4
RCC ->PLLCFGR |= 4;
RCC ->PLLCFGR &= ~(511 << 6);
RCC ->PLLCFGR |= (80 << 6); //PLLN scale80
RCC ->PLLCFGR &= ~(3 << 16); //PLLP div2
//RCC ->PLLCFGR &= ~RCC_PLLCFGR_PLLP;
RCC ->PLLCFGR |= (6 << 24); //PLLQ div3
//setting post-pll prescalers
RCC ->CFGR |= (4 << 10); //PPRE1/APB1 div2
RCC ->CFGR &= ~(7 << 13); //PPRE2/APB2 div1
RCC ->CFGR &= ~(1 << 7); //HPRE/AHB div1
//tell the PLL to use the HSE
RCC ->PLLCFGR |= (1 << 22);
//setting the main pll on
RCC ->CR |= (1 << 24);
//wait for the PLL to be ready
while (!(RCC ->CR & RCC_CR_PLLRDY));
//while (!(RCC->CR & (1<<25)));
//set the system clock input to PLL RCC_CFGR -> SW
RCC ->CFGR |= (1 << 1);
//wait for the system clock sorce to be set to PLL
while (!(RCC ->CFGR & (1 << 3)));
SystemCoreClockUpdate();
The I2C setup code:
//enable the I2C perefiral
RCC->AHB1ENR |= (1<<1); // Enable GPIOB CLOCK
RCC ->APB1ENR |= RCC_APB1ENR_I2C1EN; //enable the I2C1
//MODER:
//00: Input mode
//01: Generel prupose output mode
//10: Alternate function mode
//11: Analog mode
GPIOB ->MODER &= ~GPIO_MODER_MODE8_0; //Alternate function mode
GPIOB ->MODER |= GPIO_MODER_MODE8_1;
GPIOB ->MODER &= ~GPIO_MODER_MODE9_0; //Alternate function mode
GPIOB ->MODER |= GPIO_MODER_MODE9_1;
//OTYPER:
//0: Output push_pull (reset state)
//1: Output open-drain
GPIOB ->OTYPER |= GPIO_OTYPER_OT8; //open-drain
GPIOB ->OTYPER |= GPIO_OTYPER_OT9; //open-drain
//OSPEEDR:
//x0: Low speed
//01: Medium speed
//11: High speed
GPIOB ->OSPEEDR |= GPIO_OSPEEDER_OSPEEDR8; //High speed
GPIOB ->OSPEEDR |= GPIO_OSPEEDER_OSPEEDR9; //High speed
//PUPDR:
//00: No pull-up, pull-down
//01: Pull-up
//10: Pull-down
//11: Reserved
GPIOB ->PUPDR &= ~GPIO_PUPDR_PUPD8;
GPIOB ->PUPDR &= ~GPIO_PUPDR_PUPD9;
//GPIOB ->PUPDR |= (1 << 16) | (1 << 18);
//enable pins 8 and 9 I2C alternate function
GPIOB ->AFR[1] |= (1 << 2) | (1 << 6); //set pins PB8 and PB9 to I2C alternate-function
//reset the I2C
I2C1 ->CR1 |= (1<<15);
I2C1 ->CR1 &= ~(1<<15);
//set the I2C CR2 input clock frequency
I2C1 ->CR2 |= (40 << 0); //40 is the APB1 clock, make sure thats it is set up correctly
//CRR register
// Tr(scl) + Tw(sclh)
//CRR = -------------------
// Tpclk1
//Tr(scl) = 300ns
//Tw(sclh) = 600ns
//Tpclk1 = (1 / 40)ns = 25ns //1 over the PCLK1 frequency
//CCR = 4
I2C1 ->CCR |= (4<<0);
//TRISE register
// Tr(scl)
//TRISE = ---------- + 1
// Tpclk1
//Tr(scl) = 300ns
//Tpclk1 = (1 / 40)ns = 25ns //1 over the PCLK1 frequency
//TRISE = 12 + 1
I2C1 ->TRISE |= (13<<0);
/*
//select the I2C mode: 0 for standard and 1 for fast
I2C1 ->CCR &= ~(1 << 15);
//select the I2C CCR duty bit
I2C1 ->CCR &= ~(1 << 14); //same as the I2C mode
*/
//select the I2C mode: 0 for standard and 1 for fast
I2C1 ->CCR |= (1 << 15);
//select the I2C CCR duty bit
I2C1 ->CCR |= (1 << 14); //same as the I2C mode
//I2C perefiral enable
I2C1 ->CR1 |= (1 << 0);
I would love to have some help thanks!
Eyal
Edit:
here is the timer setup too
RCC ->APB2ENR |= (1 << 16); //enable the TIM9 clock
//timers clock is 86mhz
//TIM9 ->PSC |= 10000-1; //clock fraquency -1 to get a 10khz pulse
//TIM9 ->PSC |= 12500-1; //clock fraquency -1 to get a 10khz pulse
TIM9 ->PSC |= 8000-1; //clock fraquency -1 to get a 10khz pulse
TIM9 ->ARR |= 0xFFFF; //set the maximum value to be the max possible
TIM9 ->CR1 |= (1 << 0); //enable the timer
while (!(TIM9 ->SR & (1 << 0))); //wait for the timer ready bit to set
2022-01-19 09:03 AM
Is this a "known good" board like Nucleo/Disco? If not, you should try your code on one of those.
Looks good at the first sight. Try reading out and checking the RCC registers content. Try doing something simpler, like a blinky, check if it is rock stable. Check power supply. Check all VDD and VSS connections, including the analog. I am talking about bad solder joints. Check that voltage on VCAP is as expected and rock stable. Check VCAP connections.
JW
2022-01-19 09:05 AM
Thanks for your response! I'll check it all out.
I'm using a custom board.
Eyal
2022-01-20 05:00 AM
Hi again, I've checked all of the connections and they look good. the VCAP voltage is around 1.3V and stable, is this ok? also, the VCAP pin is connected to ground through a 4.7nF cap, is this ok?
Thanks, Eyal
2022-01-25 06:01 AM
Problem Solved!
I have noticed that I put a 4.7nF cap instead of a 4.7uF cap on the Vcap pin