Optimizations with avr-gcc

Go To Last Post
10 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hi guys,

I have a small program with the following statements -

DDRB = 0x1;

DDRB = DDRB<<2;

DDRB += 5;

I am compiling it with "avr-gcc -mmcu=atmega8 -O3 -fdump-tree-all ledchase.c". As you can see, I am dumping the content after each pass in avr-gcc.

In the dumps, I see that neither statement 2 nor 3
is optimized i.e. I don't see "DDRB = 4 (from 2nd statement)" or "DDRB = 5 (from 3rd statement)".

My question is - Is it possible to achieve such optimizations with avr-gcc? if not, why?

Another important things I would like to know if programs for AVR devices are written with such statements i.e. "DDRB = DDRB<<2" or "DDRB += 5".
Or it is mostly a direct constant value assignment to registers?

Please let me know. It would help me a lot. Thanks in advance !

Thanks and regards,
Sandeep.

Thanks and regards,
Sandeep K Chaudhary,
University of Waterloo, Canada.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

1) If this is a GCC question, then why not post in the GCC forum?
2) Please make a complete test program, and post it using the Code tags.
Alternatively, show the actual block of code with your sample statements.
3) Then, show the compiler generated code for that program, or at least the relevant part. Tell what you expect; tell what parts are not what you expect.

You can put lipstick on a pig, but it is still a pig.

I've never met a pig I didn't like, as long as you have some salt and pepper.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Quote:

I don't see "DDRB = 4 (from 2nd statement)" or "DDRB = 5 (from 3rd statement)".


You never will. It is not an optimization issue. >>You<< told the compiler: "Read the value of the volatile I/O register DDRB. Take that value and multiply it by 4. Then store the result into the volatile I/O register DDRB".

The key here is the "volatile" part. Indeed, if you code a sequence with a normal variable, not volatile, the compiler will probably just assign the final value. And if that isn't used the whole sequence might disappear (ultimate optimization).

You can put lipstick on a pig, but it is still a pig.

I've never met a pig I didn't like, as long as you have some salt and pepper.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I'll move this to the GCC forum where it belongs.

You didn't say which AVR but let's guess at mega16. So DDRB in that is defined as:

#define DDRB    _SFR_IO8(0x17)

that SFR macro is in sfr_defs.h:

#define _SFR_IO8(io_addr) _MMIO_BYTE((io_addr) + __SFR_OFFSET)

In which __SFR_OFFSET is 0x20 and _MMIO_BYTE() is:

#define _MMIO_BYTE(mem_addr) (*(volatile uint8_t *)(mem_addr))

and THERE is your "problem". DDRB is a location holding volatile uint8_t.

By it's nature volatile means "don't optimise" so you aren't going to be seeing conglomeration on multiple accesses to DDRB. Try it on a regular variable and, to prevent optimisation, either make it global or, better, make it extern in some other compilation unit. Then you will see the optimiser go to work on it.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0


DDRB = 0x1; //each statement must be executed
DDRB = DDRB<<2; //separately
DDRB += 5; //you don't know whether SFR has changed value


uint8_t var;
var = 0x1;
var = DDRB<<2;
var += 5;
DDRB = var; // I guess that var is removed. and DDRB = 9;

Think about it. SPSR or PINB might change value at any time. This is why SFRs are declared as volatile.

Mind you, DDRB or PORTB will only contain the value in the latch (from a previous assignment)

So you could argue that some SFRs are treated as non-volatile.

David.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

david.prentice wrote:
So you could argue that some SFRs are treated as non-volatile.

Nothing stopping one making one's own definitions, should one so desire...

Top Tips:

  1. How to properly post source code - see: https://www.avrfreaks.net/comment... - also how to properly include images/pictures
  2. "Garbage" characters on a serial terminal are (almost?) invariably due to wrong baud rate - see: https://learn.sparkfun.com/tutorials/serial-communication
  3. Wrong baud rate is usually due to not running at the speed you thought; check by blinking a LED to see if you get the speed you expected
  4. Difference between a crystal, and a crystal oscillatorhttps://www.avrfreaks.net/comment...
  5. When your question is resolved, mark the solution: https://www.avrfreaks.net/comment...
  6. Beginner's "Getting Started" tips: https://www.avrfreaks.net/comment...
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

s.chaudhary wrote:
I am compiling it with "avr-gcc -mmcu=atmega8 -O3 -fdump-tree-all ledchase.c". As you can see, I am dumping the content after each pass in avr-gcc.
No, not really. You are just dumping the tree passes. For more dumps, add -fdump-rtl-all -save-temps -dP.

These dumps are written by the compiler proper (cc1 or cc1plus) after preprocessing. Therefore you won't see "DDRB" anywhere because it's usually just a macro from avr/io.h. You can add -g3 so that macros are shipped in debug info, but you still won't see "DDRB" in the dumps.

avrfreaks does not support Opera. Profile inactive.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Quote:
Mind you, DDRB or PORTB will only contain the value in the latch (from a previous assignment)

"volatile" also prevents the optimization of sequences like:

PORTB = 1;
PORTB = 2;
PORTB = 4;

into

PORTB = 4;
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Thanks everyone for the reply ! I got the answer which is the 'volatile' keyword because of which the compiler doesn't do any optimizations.

Thanks and regards,
Sandeep.

Thanks and regards,
Sandeep K Chaudhary,
University of Waterloo, Canada.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

s.chaudhary wrote:
the 'volatile' keyword because of which the compiler doesn't do any (sic) optimizations.

No, that's not true.

'volatile' suppresses certain optimisations - not all optimisations.

Top Tips:

  1. How to properly post source code - see: https://www.avrfreaks.net/comment... - also how to properly include images/pictures
  2. "Garbage" characters on a serial terminal are (almost?) invariably due to wrong baud rate - see: https://learn.sparkfun.com/tutorials/serial-communication
  3. Wrong baud rate is usually due to not running at the speed you thought; check by blinking a LED to see if you get the speed you expected
  4. Difference between a crystal, and a crystal oscillatorhttps://www.avrfreaks.net/comment...
  5. When your question is resolved, mark the solution: https://www.avrfreaks.net/comment...
  6. Beginner's "Getting Started" tips: https://www.avrfreaks.net/comment...