Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Array of pointers like (*(volatile unsigned long *)0x40004000)

Tags:

c++

c

gcc

I am having a very hard time figuring out how to solve the following problem. I am on an embedded system with very little memory and want to minimize memory usage. Pointers have always confused the heck out of me and will always do.

I have a whole bunch of defines for register addresses:

#define GPIO_PORTA_BASE      (*((volatile unsigned long *)0x40004000))
#define GPIO_PORTB_BASE      (*((volatile unsigned long *)0x40005000))
//etc..

These registers are direct accessible. e.g:

GPIO_PORT_BASE &= 0x01;

What I need is an array that contains the above registers so that I can easily map them to an index. e.g:

not_sure_what_to_declare_the array_as port_base_array[] {
   GPIO_PORTA_BASE,
   GPIO_PORTB_BASE,
   //etc
}

What I need to end up being able to do is something like this:

volatile unsigned long *reg;
*reg_a = port_base_array[0];
reg_a &=0x1;

I am using gcc to compile my code for arm cortex m3.

Any insight would be appreciated.

like image 703
robertinant Avatar asked Nov 20 '11 20:11

robertinant


2 Answers

I don't know why @Etienne deleted his answer, but it contained the essential information: The address is cast to volatile unsigned long *. That's what you need an array of.

typedef volatile unsigned long* reg_addr;

reg_addr registers[] = {
  &GPIO_PORTA_BASE,
  &GPIO_PORTB_BASE,
  // ...
};

We need to take the address again (&GPIO_PORTA_BASE), since the macro automatically dereferences them. Access as:

*registers[i] &= your_value;
like image 146
Xeo Avatar answered Nov 15 '22 19:11

Xeo


Usual way is to declare a struct, for example :

struct RegsAtAddrA
{
  unsigned int array1[10];
  char val1;
  // etc
};

then to access it :

volatile RegsAtAddrA *pRegsA = (volatile RegsAtAddrA *) 0x40004000;
pRegsA->val1= 'a';
//etc

EDIT: I just realized that I haven't answered the question. So, here it is :

#include <iostream>
unsigned long a=1;
unsigned long b=2;
volatile unsigned long *port_base_array[] = {
   &a,
   &b,
   //etc
};
int main()
{
    std::cout<<"a="<<*port_base_array[0]<<std::endl;
    std::cout<<"b="<<*port_base_array[1]<<std::endl;
}
like image 25
BЈовић Avatar answered Nov 15 '22 18:11

BЈовић