Skip to main content
Visitor II
January 19, 2024
Solved

STM32G0 - G0B1RE GPIO MOD REGISTER not enabled

  • January 19, 2024
  • 2 replies
  • 1910 views

Hi, I use STM32Cube IDE, and use STM32G0 - G0B1RE device. I try to enable the mod register to blink the LED here is the code that i try so far, based on the Reference Manual (rm0444), I need to enable RCC_IOPENR before modify the GPIOx_MODER. But unfortunately it still did not work.

When i try in debugging mode via the SFRs by set the value of RCC_IOPENR, GPIOA MODER (MODER5), OTYPER (OT5), PUPDR PUPDR(5), and BSRR the LED was turned on. 

The LED is at GPIOA (PA5) based on the schematic.

Did i missed something? or there is anything to enable before I modifie the GPIOx_MODER?

In the reference manual to enable to peripheral in STMG0-G0B1RE the GPIO Bus is IOPORT not AHB or APB 

Screenshot 2024-01-19 at 09.21.06.png

Screenshot 2024-01-19 at 09.23.59.pngScreenshot 2024-01-19 at 09.24.22.pngScreenshot 2024-01-19 at 09.24.32.pngScreenshot 2024-01-19 at 09.25.00.png

 

#include "main.h"
#include "stdint.h"

int main(void)
{
 uint32_t *ptr;
 
 // RCC_IOPENR
 ptr = (uint32_t *)(0x40021000 + 0x34);
 *ptr |= (0x1 << 0); //set bit position 0 to value 1 (0x1) for GPIOA

 // GPIO MOD Register GPIOA
 // [ISSUE] THE MOD REGISTER VALUE DID NOT CHANGE
 ptr = (uint32_t *)0x50000000;
 *ptr |= (0x1 << 10);

 //OTYPE
 ptr++;
 *ptr &= ~(uint32_t)(0x1 << 5); //output type

 //PUPDR
 ptr++;
 *ptr |= (uint32_t)(0x2 << 10); //pull down

 ptr++;
 *ptr |= (0x1 << 5);//turn on led
 *ptr |= (0x1 << 21);// turn off led

}

 

 

    This topic has been closed for replies.
    Best answer by TDK

    A few things:

    The default value for MODE0 is 0b11, so setting bit 0 will not change anything since it's already set. That is expected. You should to unset bit 1 (not done) and set bit 0 (already set).

    Using the CMSIS defines will make your code much more readable. For example:

    GPIOA->MODER = (GPIOA->MODER & ~0x03) | 0x01;

    Mark the register as volatile to prevent the compiler from optimizing out changes that otherwise have no effect.

    volatile uint32_t *ptr;

     

    2 replies

    TDKAnswer
    Super User
    January 19, 2024

    A few things:

    The default value for MODE0 is 0b11, so setting bit 0 will not change anything since it's already set. That is expected. You should to unset bit 1 (not done) and set bit 0 (already set).

    Using the CMSIS defines will make your code much more readable. For example:

    GPIOA->MODER = (GPIOA->MODER & ~0x03) | 0x01;

    Mark the register as volatile to prevent the compiler from optimizing out changes that otherwise have no effect.

    volatile uint32_t *ptr;

     

    dx7Author
    Visitor II
    January 19, 2024

    Thank you for your response, but still did not work, when i try with HAL it works, but manually do from the registers it did not work, there something that keep the GPIOx_MODER value not change

     

     RCC->IOPENR = (0x1 << 0);
    
    	GPIOA->MODER = (GPIOA->MODER & ~0x03) | 0x01;
    
    	GPIOA->OTYPER = (0x0 << 10);
    
    	GPIOA->PUPDR = (0x02 << 10);
    
    	GPIOA->BSRR = (0x1 << 5);
    	GPIOA->BSRR = (0x1 << 21);

    this is the memory value for 0x50000000 (GPIOA Register)

    Screenshot 2024-01-19 at 17.22.02.png

    dx7Author
    Visitor II
    January 19, 2024

    Finally did it, thanks to @TDK for suggestion, i will accept your solution.

    Here is the working code:

    RCC->IOPENR = (0x1 << 0);
    
    GPIOA->MODER = (GPIOA->MODER & ~GPIO_MODER_MODE5_1)| 0x1; //or ~0x00000800
    
    GPIOA->OTYPER = (0x0 << 10);
    
    GPIOA->PUPDR = (0x02 << 10);
    
    GPIOA->BSRR = (0x1 << 5);
    GPIOA->BSRR = (0x1 << 21);
    
    GPIOA->BSRR = (0x1 << 5);
    GPIOA->BSRR = (0x1 << 21);

     

     

    Super User
    January 19, 2024

    Sorry, thought you were setting up PA0, not PA5. But the rationale was correct. Glad you got it working.