xelax 0 6 февраля, 2008 Опубликовано 6 февраля, 2008 · Жалоба После написания программ на arm с помощью gcc, было очень необычно для avr-gcc отсутствие явного загрузочного кода и явного lowlevelinit. Я так понимаю когда указываешь таргет mmcu, линкер сам знает какой прикомпилированный код прилинковать. А реализованно ли в этом коде забивание нулями bss секции. И где эти исходники посмотреть можно? И всегда ли при объявлении глобального массива элементов любого типа например он будет заполнен нулями? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
amw 0 6 февраля, 2008 Опубликовано 6 февраля, 2008 · Жалоба После написания программ на arm с помощью gcc, было очень необычно для avr-gcc отсутствие явного загрузочного кода и явного lowlevelinit. Я так понимаю когда указываешь таргет mmcu, линкер сам знает какой прикомпилированный код прилинковать. А реализованно ли в этом коде забивание нулями bss секции. И где эти исходники посмотреть можно? И всегда ли при объявлении глобального массива элементов любого типа например он будет заполнен нулями? Собственно lowlevelinit для меня до сих пор необычно. В GNU toolchain загрузочный код находится в файлах crt0.S, crt1.S и прочих crt*.S. Входят они в состав libc. Исходники соответственно находятся в исходниках avr-libc. Только что проинсталлировал себе ради интереса (я AVR не работаю). main.c char x[32]; int main(void) { return 0; } Компилируем avr-gcc -g3 -v -o tst main.c Using built-in specs. Target: avr Configured with: ../build-tree/gcc-4.1.0/configure -v --enable-languages=c,c++ --prefix=/usr --infodir=/usr/share/info --mandir=/usr/share/man --enable-shared --with-system-zlib --enable-long-long --enable-nls --without-included-gettext --disable-checking --disable-libssp --build=x86_64-linux-gnu --host=x86_64-linux-gnu --target=avr Thread model: single gcc version 4.1.0 /usr/libexec/gcc/avr/4.1.0/cc1 -quiet -v -dD main.c -quiet -dumpbase main.c -auxbase main -g3 -version -o /tmp/ccBz19xB.s ignoring nonexistent directory "/usr/lib/gcc/avr/4.1.0/../../../../avr/sys-include" #include "..." search starts here: #include <...> search starts here: /usr/lib/gcc/avr/4.1.0/include /usr/lib/gcc/avr/4.1.0/../../../../avr/include End of search list. GNU C version 4.1.0 (avr) compiled by GNU C version 4.1.2 20061115 (prerelease) (Debian 4.1.1-21). GGC heuristics: --param ggc-min-expand=100 --param ggc-min-heapsize=131072 Compiler executable checksum: bac81a89e3092f468be596fb2b77fc06 /usr/lib/gcc/avr/4.1.0/../../../../avr/bin/as -o /tmp/ccKrQMt1.o /tmp/ccBz19xB.s /usr/lib/gcc/avr/4.1.0/../../../../avr/bin/ld -m avr2 -o tst /usr/lib/gcc/avr/4.1.0/../../../../avr/lib/crts8515.o -L/usr/lib/gcc/avr/4.1.0 -L/usr/lib/gcc/avr/4.1.0 -L/usr/lib/gcc/avr/4.1.0/../../../../avr/lib /tmp/ccKrQMt1.o -lgcc -lc -lgcc Смотрим перечень файлов при линковке (последняя команда). Используется файл crts8515.o значит исходник будет crts8515.S (не знаю, может для AVR это crts8515.asm) Смотрим что получилось amw@fox:~/tmp$ avr-objdump -S tst > tst.dump Дамп дизассемблера. tst: file format elf32-avr Disassembly of section .text: 00000000 <__vectors>: 0: 0c c0 rjmp .+24 ; 0x1a <__ctors_end> 2: 27 c0 rjmp .+78 ; 0x52 <__bad_interrupt> 4: 26 c0 rjmp .+76 ; 0x52 <__bad_interrupt> 6: 25 c0 rjmp .+74 ; 0x52 <__bad_interrupt> 8: 24 c0 rjmp .+72 ; 0x52 <__bad_interrupt> a: 23 c0 rjmp .+70 ; 0x52 <__bad_interrupt> c: 22 c0 rjmp .+68 ; 0x52 <__bad_interrupt> e: 21 c0 rjmp .+66 ; 0x52 <__bad_interrupt> 10: 20 c0 rjmp .+64 ; 0x52 <__bad_interrupt> 12: 1f c0 rjmp .+62 ; 0x52 <__bad_interrupt> 14: 1e c0 rjmp .+60 ; 0x52 <__bad_interrupt> 16: 1d c0 rjmp .+58 ; 0x52 <__bad_interrupt> 18: 1c c0 rjmp .+56 ; 0x52 <__bad_interrupt> 0000001a <__ctors_end>: 1a: 11 24 eor r1, r1 1c: 1f be out 0x3f, r1 ; 63 1e: cf e5 ldi r28, 0x5F ; 95 20: d2 e0 ldi r29, 0x02 ; 2 22: de bf out 0x3e, r29 ; 62 24: cd bf out 0x3d, r28 ; 61 00000026 <__do_copy_data>: 26: 10 e0 ldi r17, 0x00 ; 0 28: a0 e6 ldi r26, 0x60 ; 96 2a: b0 e0 ldi r27, 0x00 ; 0 2c: e4 e6 ldi r30, 0x64 ; 100 2e: f0 e0 ldi r31, 0x00 ; 0 30: 03 c0 rjmp .+6 ; 0x38 <.do_copy_data_start> 00000032 <.do_copy_data_loop>: 32: c8 95 lpm 34: 31 96 adiw r30, 0x01 ; 1 36: 0d 92 st X+, r0 00000038 <.do_copy_data_start>: 38: a0 36 cpi r26, 0x60 ; 96 3a: b1 07 cpc r27, r17 3c: d1 f7 brne .-12 ; 0x32 <.do_copy_data_loop> 0000003e <__do_clear_bss>: 3e: 10 e0 ldi r17, 0x00 ; 0 40: a0 e6 ldi r26, 0x60 ; 96 42: b0 e0 ldi r27, 0x00 ; 0 44: 01 c0 rjmp .+2 ; 0x48 <.do_clear_bss_start> 00000046 <.do_clear_bss_loop>: 46: 1d 92 st X+, r1 00000048 <.do_clear_bss_start>: 48: a0 38 cpi r26, 0x80 ; 128 4a: b1 07 cpc r27, r17 4c: e1 f7 brne .-8 ; 0x46 <.do_clear_bss_loop> 4e: 02 d0 rcall .+4 ; 0x54 <main> 50: 08 c0 rjmp .+16 ; 0x62 <_exit> 00000052 <__bad_interrupt>: 52: d6 cf rjmp .-84 ; 0x0 <__heap_end> 00000054 <main>: char x[32]; int main(void) { 54: cf e5 ldi r28, 0x5F ; 95 56: d2 e0 ldi r29, 0x02 ; 2 58: de bf out 0x3e, r29 ; 62 5a: cd bf out 0x3d, r28 ; 61 return 0; 5c: 80 e0 ldi r24, 0x00 ; 0 5e: 90 e0 ldi r25, 0x00 ; 0 60: 00 c0 rjmp .+0 ; 0x62 <_exit> 00000062 <_exit>: 62: ff cf rjmp .-2 ; 0x62 <_exit> Наблюдаем: 0000003e <__do_clear_bss>: Что оно делает реально я не знаю. Потому как не знаю ассемблера AVR. Забыл сказать. Все это в Debian/Lenny. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
xelax 0 6 февраля, 2008 Опубликовано 6 февраля, 2008 · Жалоба :01: Что-то сам не додумался дизасм всего проекта сделать... Ступил. Спасибо за оперативный и подробный ответ. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
amw 0 6 февраля, 2008 Опубликовано 6 февраля, 2008 · Жалоба :01: Что-то сам не додумался дизасм всего проекта сделать... Ступил. Спасибо за оперативный и подробный ответ. Бывает. Наздоровье :) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Сергей Борщ 143 6 февраля, 2008 Опубликовано 6 февраля, 2008 · Жалоба После написания программ на arm с помощью gcc, было очень необычно для avr-gcc отсутствие явного загрузочного кода и явного lowlevelinit.Ну, почитать описание на avr-libc надо было. void low_level_init() __attribute__((__naked__)) __attribute__((section(".init3"))); void low_level_init() { } . Загрузочный код да, автоматом, если не укажете свой. А реализованно ли в этом коде забивание нулями bss секции. И где эти исходники посмотреть можно?Искать исходники avr-libc. Включить генерацию листинга и убедиться. И всегда ли при объявлении глобального массива элементов любого типа например он будет заполнен нулями?Если компилятор соответствует стандарту С - то да. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ReAl 0 7 февраля, 2008 Опубликовано 7 февраля, 2008 · Жалоба Ну, почитать описание на avr-libc надо было. void low_level_init() __attribute__((__naked__)) __attribute__((section(".init3"))); void low_level_init() { } А ещё лучше так: /*-- INIT_CODE(number) -------------------------------------------------- * Макрос для занесення коду в секції .init#number * * Наприклад: * INIT_CODE(1) * { * MCUCR = (1 << SRE); * XMCRA = (4 << SRL0) | (0 << SRW00); * XMCRB = (1 << XMBK); * } * * розподіл секцій для avr-gcc: * .init0 Start here after reset. * .init1 * .init2 Clear __zero_reg__, set up stack pointer. * .init3 * .init4 Initialize data and BSS. * .init5 * .init6 C++ constructors. * .init7 * .init8 * .init9 Call main(). * */ #define INIT_CODE_N(_number_,_name_)\ static void init##_name_ (void) __attribute__ ((section(".init" #_number_), naked, used));\ static void init##_name_ (void) #define _INIT_CODE(n,l) INIT_CODE_N(n,l) #define INIT_CODE(_number_) _INIT_CODE(_number_,__LINE__) xelax, avr-gcc позволяет иметь сколько угодно этих "low level init" - хоть по нескольку штук на файл (удобно - достаточно просто прилинковать модуль UART и он сам проинициализирует всё, что ему нужно), причём в разные места относительно работы запускалки - секции .init1, .init3, .init5, .init7, .init8 отданы пользователю. "функции" в секциях .init* не вызываются! они линкуются друг за дружкой без call/ret. У меня довольно популярна секция .init5 - уже стек и все переменные проинициализированы, но конструкторы ещё не начали работать. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
mdmitry 0 7 февраля, 2008 Опубликовано 7 февраля, 2008 · Жалоба Использую .init5 для инициализации периферии контроллера (регистры) и .init8 для инициализации пользовательской части программы Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться