GCC: как сказать GCC поместить функцию main в начало раздела.text?
Я только начал изучать программирование на ARM и застрял в немного раздражающей проблеме. Sourcech CodeBench Lite 2013.05-23, который я использую для компиляции моих исходных кодов (можно найти здесь: https://sourcery.mentor.com/GNUToolchain/release2449)
Что мне нужно, это сказать GCC, LD или OBJCOPY поместить скомпилированный байт-код функции 'main' в начало секции.text.
Есть ли способ добиться этого? (может через скрипт компоновщика?)
Спасибо
3 ответа
Решил проблему. Для тех, кто сталкивается с этим:
- При компиляции с GCC добавьте опцию -ffunction-section в командной строке. Это скажет GCC поместить каждую функцию в отдельный раздел. Формат имени секции будет .text.# Имя функции #, без # (то есть, если функция принадлежит секции.text [которая по умолчанию имеет значение true)).
Во-вторых, используйте скрипт компоновщика, чтобы упорядочить эти "функциональные разделы" в заключительном большом разделе.text. В качестве примера, размещение основной функции в начале секции.text приведет к созданию сценария LD, который будет выглядеть примерно так:
ENTRY(main) SECTIONS { .text : { *(.text.main); *(.text*); } }
Во-первых, посмотрите, как раздел.text определен в скрипте компоновщика по умолчанию вашего gcc (так что вам не нужно создавать его самостоятельно), вызвав его следующим образом:
gcc -Wl,-verbose
это распечатает скрипт компоновщика по умолчанию. Мой показывает это для раздела.text:
/* text: Program code section */
.text :
{
*(.text)
*(.text.*)
*(.gnu.linkonce.t.*)
}
Таким образом, чтобы функция main была первой в секции.text (а остальные должны быть смежными), вы должны установить атрибут "section" для всех других функций. Например:
void main(void);
void funct1(....) __attribute__ ((section (".text.A")));
void funct2(....) __attribute__ ((section (".text.A")));
void funct3(....) __attribute__ ((section (".text.A")));
Достаточно "приписать" прототипы функций. Таким образом, когда вы сейчас скомпилируете, функция "main" будет первой в разделе ".text", а все остальные будут следовать сразу по последовательным адресам.
Если вы хотите разместить раздел ".text" (т.е. функцию "main") по определенному адресу (например, 0x1000), не забудьте связать его с:
gcc .... -Wl,-Ttext=0x1000
Вы также можете просто поместить 'main' в отдельный раздел, используя __attribute__
:
int main (void) __attribute__ ((section ("entry")));
а затем в файле ld:
ENTRY(main)
SECTIONS
{
.text :
{
*(main)
*(.text)
}
}
Есть много других интересных __attributes__
Подробнее о них читайте здесь: http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html