ARM Technical Support Knowledge Articles

STORAGE OF LOCAL VARIABLES

Applies to: C51 C Compiler

Answer


Information in this article applies to:


QUESTION

We are trying to optimize RAM usage in our code so we can increase the stack space, and would like to know how the compiler handles local variables.

We have written the following function:

void testing(void)
{
  int m;

  for(m = 0; m < 10; ++m)
    call_functionA();
}

Is variable 'm' dynamically created on the stack, or is it statically created by the compiler at compile time and assigned a permanent memory location?

By knowing this, we hope to optimize various functions so we can make 'm' global and use it in other functions, and not affect the stack size.

ANSWER

Our compiler is a little more sophisticated than that. Below find the listing of the assembly code produced for each line of C. See that 'm' is placed in registers R6 and R7. This means that no additional RAM space is taken up (either by using the stack or a static memory location) and the access time of the variable 'm' is the fastest possible.

If the compiler runs out of registers to do this, or it is not suitable to use registers, then it uses overlaid memory locations. This means that local variables in most functions use the same few locations in memory. In the small memory model, this is in data memory and the segment is called _DATA_GROUP_. This method ensures the best possible use of the very limited data memory. So, in order to make the best use of data memory, we suggest you make as many variables local as possible.

If you want to force the compiler to use a fixed memory location for a local variable, then you can declare it as static.

If you want to analyze the assembler produced for the C you are writing, make sure the option to include assembly code in listing files is turned on. (Choose C51 Compiler from the Options menu, click on the Listing tab, and check the 'Include Assembly Code' option).

                  6          void testing(void)
                  7          {
                  8   1         int m;
                  9   1
                 10   1        for(m = 0;  m < 10; ++m)
;---- Variable 'm' assigned to Register 'R6/R7' ----
0000 E4            CLR     A
0001 FF            MOV     R7,A
0002 FE            MOV     R6,A
0003         ?C0002:
                 11   1           call_functionA();
0003 120000  R     LCALL   call_functionA
0006 0F            INC     R7
0007 BF0001        CJNE    R7,#00H,?C0008
000A 0E            INC     R6
000B         ?C0008:
000B EF            MOV     A,R7
000C 640A          XRL     A,#0AH
000E 4E            ORL     A,R6
000F 70F2          JNZ     ?C0002
                 12   1      }
0011         ?C0005:
0011 22            RET

Article last edited on: 2004-06-10 15:46:31

Rate this article

[Bad]
|
|
[Good]
Disagree? Move your mouse over the bar and click

Did you find this article helpful? Yes No

How can we improve this article?

Link to this article
Copyright © 2011 ARM Limited. All rights reserved. External (Open), Non-Confidential