avr-gcc-list
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [avr-gcc-list] Array of pointers to functions revisited...


From: Ned Konz
Subject: Re: [avr-gcc-list] Array of pointers to functions revisited...
Date: Mon, 19 Jul 2004 08:17:22 -0700
User-agent: KMail/1.6.2

On Monday 19 July 2004 6:43 am, E. Weddington wrote:

> > Which produces (on avr-gcc 3.4.0) the extremely straightforward:
>
> Which is wrong.
>
> The call_fun array above has been put into the Program Memory Space by
> using the keyword PROGMEM. Therefore, to access those values, one needs to
> pull them from Program Memory Space by using the <avr/progmem.h> API,
> pgm_read_word(), which reads a word (16 bits) from the Program Memory
> Space. This reads the specified array slot which contains the address of
> the function, which is then dereferenced and called.

Ah, right.

How about this?

/*
 avr-gcc -O3 -Wall -Wl,-Map,test.map -g -mtiny-stack -mint8 -mmcu=atmega16 -o 
test.elf test.c;
 avr-objdump -h -S  test.elf > test.lst

 R16/17 is call_fun
 R26 is X reg
 R28 is Y reg
 R30 is Z register
*/ 

#include <inttypes.h>
#include <avr/pgmspace.h>

static void fun1(void) { }
static void fun2(void) { }
static void fun3(void) { }

typedef void (PROGMEM * pFun)(void);

static pFun PROGMEM call_fun [3] = { &fun1, &fun2, &fun3 };

int main(void)
{
        uint8_t i;
        for (i = 0; i< 3; i++)
        {
                pFun p = (pFun)pgm_read_word(call_fun + i);
                p();
        }
        return 0;
}


-------- which produces:

typedef void (PROGMEM * pFun)(void);

static pFun PROGMEM call_fun [3] = { &fun1, &fun2, &fun3 };

int main(void)
{
  9a:   cf e5           ldi     r28, 0x5F       ; 95
  9c:   d4 e0           ldi     r29, 0x04       ; 4
  9e:   de bf           out     0x3e, r29       ; 62
  a0:   cd bf           out     0x3d, r28       ; 61
  a2:   12 e0           ldi     r17, 0x02       ; 2
  a4:   c0 e0           ldi     r28, 0x00       ; 0
  a6:   d0 e0           ldi     r29, 0x00       ; 0
        uint8_t i;
        for (i = 0; i< 3; i++)
        {
                pFun p = (pFun)pgm_read_word(call_fun + i);
  a8:   ce 01           movw    r24, r28
  aa:   8c 5a           subi    r24, 0xAC       ; 172
  ac:   9f 4f           sbci    r25, 0xFF       ; 255
  ae:   fc 01           movw    r30, r24
  b0:   25 91           lpm     r18, Z+
  b2:   34 91           lpm     r19, Z
                p();
  b4:   f9 01           movw    r30, r18
  b6:   09 95           icall
  b8:   11 50           subi    r17, 0x01       ; 1
  ba:   22 96           adiw    r28, 0x02       ; 2
  bc:   17 ff           sbrs    r17, 7
  be:   f4 cf           rjmp    .-24            ; 0xa8
        }
        return 0;
}
  c0:   80 e0           ldi     r24, 0x00       ; 0
  c2:   0c 94 63 00     jmp     0xc6

000000c6 <_exit>:
  c6:   ff cf           rjmp    .-2             ; 0xc6


-- 
Ned Konz
http://bike-nomad.com



reply via email to

[Prev in Thread] Current Thread [Next in Thread]