Jump to content

    
Sign in to follow this  
MaxiMuz

Keil: Размещение массива обьявленного квалификатором 'const'

Recommended Posts

Интересует под Keil где описывается правило размещения данных или массива данных обьявленных как const. Размещаются ли они в ОЗУ или в памяти программ ?

Например:

const u8 CodeKey[12]={1,4,7,11,2,5,8,10,3,6,9,12};

Share this post


Link to post
Share on other sites

Если используется скрипт компоновщика (linker), то это задается в нем. Если скрипты явно не используются, то либо это настраивается через параметры командной строки компоновщика, либо Keil сам втихую генерирует скрипт на основе настроек проекта и втихую передает компоновщику, я точно не помню. В общем все упирается в компоновщик и настройку расположения секции, в которую помещаются константные данные (не помню в какую).

Edited by menzoda

Share this post


Link to post
Share on other sites

Можно просто и быстро проверить, что происходит - поискать в выводе линкера (двойной клик на самой первой строчке в дереве проекта с названием таргета) слово "CodeKey" (т.е. название Вашего массива).

Дальше внимательно смотрим, по какому адресу оно расположилось, и ищем соответствующий диапазон в документации.

 

Кейл под арм по умолчанию затолкает такой массив во флеш.

Кейл под 51-й видел только в страшном сне (надо было в чужом проекте две строки поменять).

Share this post


Link to post
Share on other sites
Размещаются ли они в ОЗУ или в памяти программ ?

Добавлю, что по идее данные размещаются в памяти программ, а во время исполнения копируются в ОЗУ и дальнейшая работа происходит именно с копией массива в ОЗУ.

 

Share this post


Link to post
Share on other sites
Добавлю, что по идее данные размещаются в памяти программ, а во время исполнения копируются в ОЗУ и дальнейшая работа происходит именно с копией массива в ОЗУ.

 

Это плохая идея в мире контроллеров, у которых ОЗУ и без того мало.

 

Share this post


Link to post
Share on other sites
Интересует под Keil где описывается правило размещения данных или массива данных обьявленных как const. Размещаются ли они в ОЗУ или в памяти программ ?

Например:

const u8 CodeKey[12]={1,4,7,11,2,5,8,10,3,6,9,12};

расположится во флеш. Можно проверить, посмотрев .map-файл

 

Добавлю, что по идее данные размещаются в памяти программ, а во время исполнения копируются в ОЗУ и дальнейшая работа происходит именно с копией массива в ОЗУ.

это если не объявлено const и содержимое массива можно изменять

Share this post


Link to post
Share on other sites
Добавлю, что по идее данные размещаются в памяти программ, а во время исполнения копируются в ОЗУ и дальнейшая работа происходит именно с копией массива в ОЗУ.

Под AVR GCC как раз так и происходило , пока на добавишь квалификатор PROGMEM

Share this post


Link to post
Share on other sites

Попробывал 3 варианта:

- массив без const

- массив c const

- баз массива.

Меняется только размер кода , RO , RW и ZI - остаются прежними.

Вывод: независимо от квалификатора const массив адресуется из флеш-памяти.

Share this post


Link to post
Share on other sites
Вывод: независимо от квалификатора const массив адресуется из флеш-памяти.

А Вы в своем коде значение ячеек массива изменяете? И выводы делаете по map файлу?

Share this post


Link to post
Share on other sites
А Вы в своем коде значение ячеек массива изменяете? И выводы делаете по map файлу?

Значение ячеек не меняю и вывод делаю по :

Program Size: Code=4372 RO-data=320 RW-data=72 ZI-data=1776

размеры областей не мяняются

Share this post


Link to post
Share on other sites

А обращение к массиву производите? Вынесите его в глобальную область.

А так создается впечатление, что компилятор просто выбросил этот массив за ненадобностью

Приведите все варианты для const и и обычного массива (с инициализацией при объявлении и глобального) размеров областей, что-то Вы упускаете, отсюда и странные результаты

Share this post


Link to post
Share on other sites
Значение ячеек не меняю

Если не использовать массив, то компилятор проявит смекалку и "соптимизирует" его помножив на ноль. Поэтому и советую (не только я) Вам делать выводы по map файлу.

Share this post


Link to post
Share on other sites

в общем так.

const unsigned char __test[] = {
    0xC2, 0x47, 0x05, 0x31, 0x21, 0x00, 0x00, 0x04, 0x00, 0x03, 0x00, 0x00, 0x02, 0x07, 0x6F, 0x00,
    0x03, 0x00, 0x33, 0x02, 0x09, 0xCC, 0x00, 0x03, 0x00, 0x43, 0x02, 0x06, 0x00, 0x00, 0x03, 0x00,
    0x53, 0x02, 0x06, 0x00, 0x03, 0xFF, 0x00, 0x80, 0x90, 0xE6, 0xB9, 0xE0, 0x70, 0x03, 0x02, 0x01,
    0x5C, 0x14, 0x70, 0x03, 0x02, 0x02, 0x05, 0x24, 0xFE, 0x70, 0x03, 0x02, 0x02, 0x9D, 0x24, 0xFB,
    0x70, 0x03, 0x02, 0x01, 0x56, 0x14, 0x70, 0x03, 0x02, 0x01, 0x50, 0x14, 0x70, 0x03, 0x02, 0x01,
    0x44, 0x14, 0x70, 0x03, 0x02, 0x01, 0x4A, 0x24, 0x05, 0x60, 0x03, 0x02, 0x03, 0x0E, 0x12, 0x09,
    0xD5, 0x40, 0x03, 0x02, 0x03, 0x1A, 0x90, 0xE6, 0xBB, 0xE0, 0x24, 0xFE, 0x60, 0x2C, 0x14, 0x60,
    0x47, 0x24, 0xFD, 0x60, 0x16, 0x14, 0x60, 0x31, 0x24, 0x06, 0x70, 0x66, 0xE5, 0x23, 0x90, 0xE6
};

Сейчас проверил - даже если массив глобальный, но к нему нет обращения, компилятор его просто выбрасывает, о чем честно говорит в map-файле:

Removing start.o(.constdata), (128 bytes)

Program Size: Code=19456 RO-data=1456 RW-data=180 ZI-data=7132

 

Если же я явно указываю место размещения, компилятору уже некуда деваться и он просто обязан разместить массив во флэш:

const unsigned char __test[] __at(0x00007000) = { ...

map

__test                                   0x00007000   Data         128  start.o(.ARM.__AT_0x00007000)

результат

Program Size: Code=19456 RO-data=9344 RW-data=180 ZI-data=7132

Share this post


Link to post
Share on other sites
Если не использовать массив, то компилятор проявит смекалку и "соптимизирует" его помножив на ноль. Поэтому и советую (не только я) Вам делать выводы по map файлу.

Обьявлял массив в прерывании , и там же читал из него в глобальную volatile-переменную , которая использовалась в main-е. При этом в map файле упоминания массива я не нашел.

 

Потом, переместил массив в обл.глобальных переменных, RO увеличилось на несколько единиц, но в map-файле указание на область data - это значит область данных ?

 CodeKey                                  0x0800125e   Data          12

 

но в map-файле указание на область data - это значит область данных ?

А, понял! адрес 0x0800125e - область кода.

 

Как только убираю const , переменная перемещается в SRAM

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Sign in to follow this