|
Вопрос по работе с EEPROM в WinAVR, срочно нужна помощь |
|
|
|
May 25 2007, 07:09
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 22-12-06
Пользователь №: 23 780

|
Здравствуйте! Прошу помочь. Нужны функции записи и чтения из/в EEPROM AT90CAN128. Беру примеры из Даташита и компилирую WinAVR, не работают. Преверяю в AVRStudio - не работают. Вот эти функции из Даташита:
/********************************* * * ЗАПИСЬ БАЙТА В int-EEPROM * *********************************/ void RTEEPROMwrite (u16 adrEEPROM, u08 databyte) { u08 savedSREG; while(EECR & (1<<EEWE)); savedSREG = SREG // keep setting so it can be restored SREG &= ~0x80; EEAR = adrEEPROM; // set address EEDR = databyte; // set data EECR |= (1<<EEMWE); // set "write enable" bit EECR |= (1<<EEWE); // set "write" bit SREG = savedSREG; // restore SREG EEAR = 0;
} // end of RTEEPROMwrite
/********************************** * * ЧТЕНИЕ БАЙТА ИЗ int-EEPROM * **********************************/ u08 RTEEPROMread (u16 adrEEPROM) { while(EECR & (1<<EEWE)); EEAR = adrEEPROM; // set address EECR |= (1<<EERE); // set "read enable" bit EEAR = 0; return (EEDR);
} // end of RTEEPROMread
Хотел использовать функции из библиотеки:
uint8_t eeprom_read_byte (const uint8_t *addr);
void eeprom_write_byte (uint8_t *addr,uint8_t value);
Но не понятно как описать и работать с указателями на ячейки в EEPROM.
|
|
|
|
|
May 25 2007, 08:42
|
Знающий
   
Группа: Участник
Сообщений: 596
Регистрация: 26-05-06
Из: Москва
Пользователь №: 17 484

|
Цитата(AlexPT @ May 25 2007, 11:09)  Здравствуйте! Прошу помочь. Нужны функции записи и чтения из/в EEPROM AT90CAN128. Беру примеры из Даташита и компилирую WinAVR, не работают. Преверяю в AVRStudio - не работают. Вот эти функции из Даташита: С каким уровнем оптимизации компилируете? Состояния фюза M103C? Анатолий. Цитата(Tcom @ May 25 2007, 11:32)  unsigned char EEPROM_read (unsigned int uiAdress)// Чтение eeprom { while (EECR & (1<<EEWE)); EEAR = uiAdress; EECR |= (1<<EERE); return EEDR;} void EEPROM_write(unsigned int uiAdress , unsigned char ucData) // Запись eeprom { while(EECR & (1<<EEWE)); EEAR = uiAdress ; EEDR = ucData; EECR |= (1<<EEMWE); EECR |= (1<<EEWE); }
Вот рабочий пример с моей проги под WinAVR омпилятор. А что будет если между строками EECR |= (1<<EEMWE); EECR |= (1<<EEWE); произойдет прерывание? Анатолий.
|
|
|
|
|
May 25 2007, 09:56
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 22-12-06
Пользователь №: 23 780

|
С EEAR = 0 это опечатка. Компилирую с уровнем оптимизации 0. Что такое фюз М103С я не знаю (я только недавно начал работать с WinAVR, так что прошу отнестисть с пониманием), но такого слова в makefile нет. Хотелось бы по подробнее узнать по приведению типа u16 к типу const uint8_t*. Если можно поясните на примере. Приведенный пример попробывал, не работает да он практически не отличается Даташитовского. Может необходима какая-то запись в makefile или .h файлы.
|
|
|
|
|
May 25 2007, 10:12
|
Знающий
   
Группа: Участник
Сообщений: 596
Регистрация: 26-05-06
Из: Москва
Пользователь №: 17 484

|
Цитата(AlexPT @ May 25 2007, 13:56)  С EEAR = 0 это опечатка. Компилирую с уровнем оптимизации 0. Что такое фюз М103С я не знаю Про М103С извините ошибся, подумал что речь идет о ATmega128. Посмотрите код который генериться для строк: EECR |= (1<<EEMWE); EECR |= (1<<EEWE); Не уровне оптимизации -O0: Код EECR |= (1<<EEMWE); 92: 80 91 3c 00 lds r24, 0x003C 96: 84 60 ori r24, 0x04; 4 98: 80 93 3c 00 sts 0x003C, r24 EECR |= (1<<EEWE); 9c: 80 91 3c 00 lds r24, 0x003C a0: 82 60 ori r24, 0x02; 2 a2: 80 93 3c 00 sts 0x003C, r24 И на -O1: Код EECR |= (1<<EEMWE); 8e: e2 9a sbi 0x1c, 2; 28 EECR |= (1<<EEWE); 90: e1 9a sbi 0x1c, 1; 28 В первом случае не соблюдается условие установки бита EEWE не позже 4 циклов после установки EEMWE. Не используйте уровень оптимизации -O0, он нужен в очень редких случаях для отладки. Используйте библиотечные функции, как с ними работать описано в avr-libc-user-manual в директори WinAVR/doc/avr-libc. Анатолий.
Сообщение отредактировал aesok - May 25 2007, 10:16
|
|
|
|
|
May 25 2007, 11:02
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 22-12-06
Пользователь №: 23 780

|
Большое спасибо за подсказку с оптимизацией. Все заработало.
|
|
|
|
|
Sep 29 2010, 22:10
|

Частый гость
 
Группа: Участник
Сообщений: 82
Регистрация: 1-03-10
Пользователь №: 55 731

|
добрый вечер решил поднять тему, просто проблема с Atmega128 в WinAVR как и у автора почти Код unsigned char EEPROM_read(unsigned int uiAdress)// Чтение { while (EECR & (1<<EEWE)); EEAR = 0x10; EECR |= (1<<EERE); return EEDR; }
void EEPROM_write(unsigned int uiAdress , unsigned char ucData) // Запись { char cSREG; while(EECR & (1<<EEWE)); EEAR = uiAdress; EEDR = ucData;
cSREG = SREG; cli(); EECR |= (1<<EEMWE); EECR |= (1<<EEWE); SREG = cSREG; } функция записи почему то не работает, так как читаю постоянно 0xff оптимизация -O1 подскажите пожалуйста в чем дело
|
|
|
|
|
Sep 30 2010, 04:51
|
Местный
  
Группа: Участник
Сообщений: 298
Регистрация: 26-01-09
Из: Пермь
Пользователь №: 43 940

|
используйте библиотечные функции. Например, для записи Код eeprom_write_word ((void*)0x10, power_s ); eeprom_write_word ((void*)0x12, syplsec ); eeprom_write_word ((void*)0x14, worksec ); Например, для чтения (в цикле) Код #define EEPROM_BASE 0x10 for(byte i=0; i<PARAM_COUNT; i++) sav_param.masu[i] = eeprom_read_word((void *)(EEPROM_BASE + i*sizeof(word)));
|
|
|
|
|
Sep 30 2010, 06:40
|

Профессионал
    
Группа: Участник
Сообщений: 1 091
Регистрация: 25-07-07
Из: Саратов
Пользователь №: 29 357

|
Цитата(aesok @ May 25 2007, 14:12)  Посмотрите код который генериться для строк: EECR |= (1<<EEMWE); EECR |= (1<<EEWE);
Не уровне оптимизации -O0: -O0 это полное отсутствие оптимизации, компилировать программу без нее глупо. Обычно это импользуется тогда, когда вы подозреваете оптимизатор в глючности, тогда отключив оптимизацию можно убедиться, что проблема в самой программе. Обычно для боевой программы используется уровень -Os Цитата(AlexPT @ May 25 2007, 11:09)  savedSREG = SREG // keep setting so it can be restored SREG &= ~0x80; А к чему такие сложности? Не проще ли написать cli(), sei()
|
|
|
|
|
Sep 30 2010, 06:50
|
Знающий
   
Группа: Участник
Сообщений: 596
Регистрация: 26-05-06
Из: Москва
Пользователь №: 17 484

|
Цитата(777777 @ Sep 30 2010, 10:40)  -O0 это полное отсутствие оптимизации, .... Обычно для боевой программы используется уровень -Os Спасибо большое, я об этом уже 3 года как не знаю, побегу сейчас на рабору перекомпилирую проект, может заработаент!!! Цитата(777777 @ Sep 30 2010, 10:40)  А к чему такие сложности? Не проще ли написать cli(), sei() Такие сложности нужны для того, чтобы функция EEPROM_write делала только то что от нее требуется - записывала байт в EEPROM, и не делела то чего не должна, тоесть чтобы она не разрешала прерывания. Анатолий.
|
|
|
|
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|