реклама на сайте
подробности

 
 
> pgm_read_xxxx и PROGMEM в winavr20071221, В листинге нет инструкций LPM
Steel_monkey
сообщение Mar 3 2008, 17:18
Сообщение #1


Участник
*

Группа: Участник
Сообщений: 25
Регистрация: 12-05-07
Из: Северная Венеция
Пользователь №: 27 684



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

Мои действия?
1. Присоединяю библиотеку avr/pgmspace.h
2. Обьявляю массив:
uint16_t left[] PROGMEM = {60,0x93,45,70};
3. В программе читаю из массива:
REQUIRED_LEFT=pgm_read_word(&left[1]);
Переменная, куда читаю, точно такого же типа, что и в массиве.
Смотрю в файл main.lst

254:main.c **** REQUIRED_LEFT=pgm_read_word(&left[1]);
905 .LM96:
906 03b0 80E0 /* #NOAPP */
907 03b2 90E0 mov r18,r26
908 03b4 FC01 subi r18,lo8(-(1))
909 sts point.1941,r18
911 03b8 5491 .LM97:
912 cpi r18,lo8(4)
913 brlo .L50
915 03ba 5093 0000 .LM98:
916 03be 4093 0000 sts point.1941,__zero_reg__


В файле нет инструкции LPM.

4. Убираем закорючку:
REQUIRED_LEFT=pgm_read_word(left[1]);

Тогда это превращается в

254:main.c **** REQUIRED_LEFT=pgm_read_word(left[1]);
905 .LM96:
906 03b0 E3E9 /* #NOAPP */
907 03b2 F0E0 mov r18,r26
908 subi r18,lo8(-(1))
909 03b4 8591 sts point.1941,r18
911 .LM97:
912 cpi r18,lo8(4)
913 brlo .L50
915 03bc 8093 0000 .LM98:


Инструкция LPM в коде так и не появилась.
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
Steel_monkey
сообщение Mar 3 2008, 19:44
Сообщение #2


Участник
*

Группа: Участник
Сообщений: 25
Регистрация: 12-05-07
Из: Северная Венеция
Пользователь №: 27 684



Обьявлена как глобальная volotile static, щас убрал и то, и другое, то есть осталась только глобальной. Тут еще разные чудеса происходили, типа как если добавить произвольный массив PRGMEM, и ничего с ним не делать, то LPM есть, а если убрать, то нет.
В конце концов, заработало. Не знаю, где был косяк, но опять смоделировать пропадение LPM не смог. В общем вывод делаю такой, до самого Си надо изучать компилятор и его причуды, причем не меньше, чем сам Си.
А за направление в правильное русло спасибо.

Сообщение отредактировал Steel_monkey - Mar 3 2008, 19:45
Go to the top of the page
 
+Quote Post
_Pasha
сообщение Mar 4 2008, 07:40
Сообщение #3


;
******

Группа: Участник
Сообщений: 5 646
Регистрация: 1-08-07
Пользователь №: 29 509



Цитата(Steel_monkey @ Mar 3 2008, 22:44) *
Не знаю, где был косяк, но опять смоделировать пропадение LPM не смог. В общем вывод делаю такой, до самого Си надо изучать компилятор и его причуды, причем не меньше, чем сам Си.


1. Как только компилер увидит константное выражение, он выдаст его результат - нафига ему LPM ?
2. Это не причуды, а кривоватая концепция, не позволяющая автоматизировать обращение к флешу и еепрому. То есть он (компилер) достаточно умный, но соответствия стандартам порождают некоторые казусы. К примеру(из другой области) - если следовать идеологии:
Код
uint8_t j;
for(j=0;j<256;j++){do_something();}


Или не мудрствовать лукаво
Код
char j;
for(j=0;j<256;j++){do_something();}


то в последнем случае код будет короче
Go to the top of the page
 
+Quote Post
Steel_monkey
сообщение Mar 4 2008, 11:07
Сообщение #4


Участник
*

Группа: Участник
Сообщений: 25
Регистрация: 12-05-07
Из: Северная Венеция
Пользователь №: 27 684



Цитата(_Pasha @ Mar 4 2008, 10:40) *
1. Как только компилер увидит константное выражение, он выдаст его результат - нафига ему LPM ?

Дык в том и проблема, что мне нужна не отдельная константа, которую он может загрузить скажем через ldi и которая хранится априори в памяти программ, а массив констант, который хранится изначально и в ОЗУ и в ПЗУ. И тут уже как я понимаю только LPM.
А вообще смотря по англоязычным форумам, PROGMEM вызывает довольно много вопросов по работоспособности.

Сообщение отредактировал Steel_monkey - Mar 4 2008, 11:15
Go to the top of the page
 
+Quote Post
aesok
сообщение Mar 4 2008, 12:23
Сообщение #5


Знающий
****

Группа: Участник
Сообщений: 596
Регистрация: 26-05-06
Из: Москва
Пользователь №: 17 484



Цитата(Steel_monkey @ Mar 4 2008, 14:07) *
Дык в том и проблема, что мне нужна не отдельная константа, которую он может загрузить скажем через ldi и которая хранится априори в памяти программ, а массив констант, который хранится изначально и в ОЗУ и в ПЗУ. И тут уже как я понимаю только LPM.

Данные размещеют в памяти пограм как раз для того чтобы чтобы они не занимали место в RAM.
Цитата
А вообще смотря по англоязычным форумам, PROGMEM вызывает довольно много вопросов по работоспособности.

Не по работоспособности а по пониманию.

Посути вашенго вопроса. Ассемблерный код который вы привели не похож на код макроса pgm_read_word, возможно сбилось соответствие между С и ассемблерным кодом в файле с лстингом, таеое бывает. Поищите в листинге инструкции LPM/ELPM. Если нет, шлите минимальный неработающий пример.


PS:
Цитата
1. Присоединяю библиотеку avr/pgmspace.h

И давайте разберемся с терминологией: avr/pgmspace.h - это не билиотека а заголовычный файл, и он не присоединяеться а включаеться.

Анатолий.

Сообщение отредактировал aesok - Mar 4 2008, 12:30
Go to the top of the page
 
+Quote Post



Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 25th June 2025 - 07:10
Рейтинг@Mail.ru


Страница сгенерированна за 0.01399 секунд с 7
ELECTRONIX ©2004-2016