This article describes two methods of placing multiple functions or variables in a specified section without using multiple #pragma location directives.
You can place a function (or variable) in a named section using #pragma location, for example:
#pragma location = “MY_FUNC”
void f (void);
However, when there are multiple functions (or variables) to be placed, using #pragma location becomes impractical.
These methods are described below:
Use a single pragma directive to place multiple functions/variables.
Use linker placement directives to place multiple functions from object files.
Placing multiple functions/variables using a single pragma directive
There are two pragma directives that can be used to set the default location and attributes of function/variable declarations and definitions:
#pragma default_variable_attributes
#pragma default_function_attributes
These two pragma directives allow you to use one pragma directive for multiple declarations and definitions instead of using multiple pragma positional directives.
Examples of using these pragma directives
In the source code, put some functions in the MY_FUNC section:
-------------------------------------------------- -------
#pragma default_function_attributes = @ "MY_FUNC"
int fun1(int x)
{
return x + 1;
}
int fun2(int x)
{
return x - 1;
}
/* The stop function is placed in the MY_FUNC section*/
#pragma default_function_attributes =
int fun3(int x)
{
return x + x;
}
-------------------------------------------------- ---------------
/* Place the following data in the MY_DATA section */
#pragma default_variable_attributes = @ "MY_DATA"
int data1;
int data2;
/* Stop placing the following data in the MY_DATA segment */
#pragma default_variable_attributes =
int data3;
int main()
{
data1 = fun1(5);
data2 = fun2(5);
data3 = fun3(5);
return data1 + data2 + data3;
}
Add the following line to the linker configuration file (.icf) to place all data within the specified memory address range of the MY_DATA segment:
define region DATA_region = mem:[from
0x20000000to 0x20001FFF ];
place in DATA_region { readwrite section MY_DATA };
Add the following line to the linker configuration file to place all code within the specified memory address range of the MY_FUNC segment:
define region FUNC_region = mem:[ from 0x70000 to 0x70FFF ];
place in FUNC_region { readonly section
MY_FUNC };
Placing multiple functions in an object file using linker placement directives
A more convenient approach than using multiple #pragma location is to put these functions in separate source files and let the linker select all functions from the object file using the place in directive.
Here are the steps:
1. Collect functions in one (or more) source files.
2. Delete any #pragma location directives that were used previously.
3. Edit the .icf file and add a place in the directive containing the keyword object, as shown below.
Add the following line to the linker configuration file to place all code in the source file Utilities.c in the specified memory address range:
define region UTILITIES_region = mem:[ from 0x71000 to 0x71FFF ];
place in UTILITIES_region { readonly object Utilities.o };
There is no need to use multiple #pragma location directives to place data/code in a specified memory address range. You can use the method provided above as needed.
This content is originally created by MamoYU , a user on the EEWORLD forum. If you want to reprint or use it for commercial purposes, you must obtain the author's consent and indicate the source