Este tópico é uma alteração do exemplo demonstrado anteriormente com funções em assembly.
Acessando Registradores Mapeados em Memória
Os registradores estão mapeados em memória e portanto são acessados a partir de endereços únicos. Isto é, cada registrador possui uma posição fixa na memória. Para entender a estrutura básica de um registrador e as operações para configurá-los, acesse o conteúdo sobre programação de periféricos mapeados em memória.
Utilizando a linguagem C, basta indicar o endereço e realizar o acesso via ponteiro:
*endereço = valor;
Tal procedimento é mostrado a seguir.
#include<stdint.h>#defineSIM_SCGC5 (*(volatileuint32_t*)0x40048038)#definePORTB_PCR18 (*(volatileuint32_t*)(0x4004A000+4*18))#defineGPIOB_PDOR (*(volatileuint32_t*)0x400FF040)#defineGPIOB_PSOR (*(volatileuint32_t*)0x400FF044)#defineGPIOB_PCOR (*(volatileuint32_t*)0x400FF048)#defineGPIOB_PTOR (*(volatileuint32_t*)0x400FF04C)#defineGPIOB_PDIR (*(volatileuint32_t*)0x400FF050)#defineGPIOB_PDDR (*(volatileuint32_t*)0x400FF054)#defineRED_MASK (1<<18)voidredon(void){//ativar o bit 18 do registrador PCOR.//GPIOB_PCOR = (RED_MASK);//ou desativar somente o bit 18 do registrador PDOR GPIOB_PDOR = GPIOB_PDOR &~(RED_MASK);}voidredoff(void){//ativar o bit 18 do registrador PSOR.//GPIOB_PSOR = (RED_MASK);//ou ativar somente o bit 18 do registrador PDOR GPIOB_PDOR = GPIOB_PDOR | (RED_MASK);}voidinit_gpio(void){//ativar somente o bit 10 do registrador SCGC5. SIM_SCGC5 = SIM_SCGC5 | (1<<10);//ativar o bit 8 do registrador PORTB_PCR18 PORTB_PCR18 = (1<<8);//ativar o bit 18 do registrador PDDR GPIOB_PDDR = (RED_MASK);}intmain(){//configurações iniciaisinit_gpio();while(1){//programa em loop infinitoredon();redoff(); }return0;}
Encapsulando Registradores
Os registradores podem ser agrupados em uma estrutura de dados para facilitar o acesso. Por exemplo, os registradores GPIOB_PDOR até GPIOB_PDDR estão posicionados sequencialmente na memória. Esse grupo de registradores é denominado GPIOB.
Com o novo tipo de dado, basta associar o nome do módulo ao endereço base da mesma.
#defineGPIOB ((volatilestruct GPIO *)0x400FF040)
Cabe ressaltar que utilizando essa técnica outros módulos de GPIO podem ser acessados, pois apresentam a mesma sequência. Isto é, a estrutura do módulo é a mesma, a única diferença é o endereço dos registradores.
#include<stdint.h>#defineSIM_SCGC5 (*(volatileuint32_t*)0x40048038)#definePORTB_PCR18 (*(volatileuint32_t*)(0x4004A000+4*18))struct GPIO{uint32_t PDOR;uint32_t PSOR;uint32_t PCOR;uint32_t PTOR;uint32_t PDIR;uint32_t PDDR;};#defineGPIOB ((volatilestruct GPIO *)0x400FF040)#defineRED_MASK (1<<18)voidredon(void){//ativar o bit 18 do registrador PCOR.//GPIOB->PCOR = (RED_MASK);//ou desativar somente o bit 18 do registrador PDORGPIOB->PDOR =GPIOB->PDOR &~(RED_MASK);}voidredoff(void){//ativar o bit 18 do registrador PSOR.//GPIOB->PSOR = (RED_MASK);//ou ativar somente o bit 18 do registrador PDORGPIOB->PDOR =GPIOB->PDOR | (RED_MASK);}voidinit_gpio(void){//ativar somente o bit 10 do registrador SCGC5. SIM_SCGC5 = SIM_SCGC5 | (1<<10);//ativar o bit 8 do registrador PORTB_PCR18 PORTB_PCR18 = (1<<8);//ativar o bit 18 do registrador PDDRGPIOB->PDDR = (RED_MASK);}intmain(){//configurações iniciaisinit_gpio();while(1){//programa em loop infinitoredon();redoff(); }return0;}