Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: Tiny24 не пишет в EEPROM
Форум разработчиков электроники ELECTRONIX.ru > Сайт и форум > В помощь начинающему
smk
в даташит есть такие примеры:

unsigned char EEPROM_read_8 (unsigned char Address)
{
while (EECR & (1<<EEPE));
EEARL= Address;
EECR |= (1<<EERE);
return EEDR;
}

void EEPROM_write_8(unsigned char Address, unsigned char Data)
{
while (EECR & (1<<EEPE));
EECR = (0<<EEPM1) | (0>>EEPM0);
EEARL= Address;
EEDR = Data;
EECR |= (1<<EEMPE);
EECR |= (1<<EEPE);
}


на их основе сделаны функции:

unsigned int EEPROM_read_16 (unsigned char AddressH, unsigned char AddressL )
{
unsigned int Data_eep_16;
Data_eep_16=EEPROM_read_8(AddressH);
Data_eep_16=(Data_eep_16<<8);
Data_eep_16=Data_eep_16+EEPROM_read_8(AddressL);
return Data_eep_16;
}

void EEPROM_write_16 (unsigned char AddressH, unsigned char AddressL, unsigned int Data)
{
unsigned int Data_eep_8;
Data_eep_8=(Data>>8);
EEPROM_write_8(AddressH, Data_eep_8);
Data_eep_8=(char) Data;
EEPROM_write_8(AddressL, Data_eep_8);
}

перед записью всегда запрещаются прерывания:
cli();
фуз EESAVE=1, тактовая - 8 МГц, внутренний RC.
В AVR Studio 4.13 все симулируется правильно, запись происходит. Программатором EEPROM пишется исправно.

Нет записи в EEPROM в ходе выполнения программы, не пойму почему. Прошу помочь разобраться. Заранее благодарен.
smk
Ну хоть подскажите кто как делает, может сам догадаюсь...
mdmitry
Цитата(smk @ Jan 30 2008, 17:35) *
в даташит есть такие примеры:

unsigned char EEPROM_read_8 (unsigned char Address)
{
while (EECR & (1<<EEPE));
EEARL= Address;
EECR |= (1<<EERE);
return EEDR;
}

void EEPROM_write_8(unsigned char Address, unsigned char Data)
{
while (EECR & (1<<EEPE));
EECR = (0<<EEPM1) | (0>>EEPM0);
EEARL= Address;
EEDR = Data;
EECR |= (1<<EEMPE);
EECR |= (1<<EEPE);
}
на их основе сделаны функции:

unsigned int EEPROM_read_16 (unsigned char AddressH, unsigned char AddressL )
{
unsigned int Data_eep_16;
Data_eep_16=EEPROM_read_8(AddressH);
Data_eep_16=(Data_eep_16<<8);
Data_eep_16=Data_eep_16+EEPROM_read_8(AddressL);
return Data_eep_16;
}

void EEPROM_write_16 (unsigned char AddressH, unsigned char AddressL, unsigned int Data)
{
unsigned int Data_eep_8;
Data_eep_8=(Data>>8);
EEPROM_write_8(AddressH, Data_eep_8);
Data_eep_8=(char) Data;
EEPROM_write_8(AddressL, Data_eep_8);
}

unsigned int Data_eep_8;
и
void EEPROM_write_8(unsigned char Address, unsigned char Data)
не стыкуются по типам данных 16 и 8 бит.
Включите ВСЕ предупреждения компилятора и внимательно их проанализируйте.
smk
Цитата
unsigned int Data_eep_8;
и
void EEPROM_write_8(unsigned char Address, unsigned char Data)
не стыкуются по типам данных 16 и 8 бит.

сделал так:
void EEPROM_write_16 (unsigned char AddressH, unsigned char AddressL, unsigned int Data)
{
unsigned char Data_eep_8;
Data_eep_8=(Data>>8);
EEPROM_write_8(AddressH, Data_eep_8);
Data_eep_8=(char) Data;
EEPROM_write_8(AddressL, Data_eep_8);
}
Цитата
Включите ВСЕ предупреждения компилятора и внимательно их проанализируйте.

а как это сделать я не знаю

Вот эта строчка не выполняется. Без видимых причин.
EECR |= (1<<EEPE);
переписал:
EECR |= (1<<1);
не помогло.

был уровень оптимизации -О0. включил -О1. стала выполняться(на симуляторе). Что это было?
Baser
Цитата(smk @ Jan 30 2008, 16:35) *
EECR = (0<<EEPM1) | (0>>EEPM0);

Если убрать эту явную ляпу, то все должно работать (хотя и с этой ляпой тоже ничего не меняется):
Код
EECR = (0<<EEPM1) | (0<<EEPM0);

Технология программирования copy/paste позволяет обойти массу ошибок smile.gif

Ну и еще сложно вы функции пишете (правильно, но вычурно). Можно так:
Код
unsigned int EEPROM_read_16 (unsigned int Address)
  {
  unsigned int Data;
  
  Data = (unsigned int)(EEPROM_read_8(Address>>8))<<8;
  return Data | EEPROM_read_8(Address);
  }

void EEPROM_write_16 (unsigned int Address, unsigned int Data)
  {
  EEPROM_write_8(Address, Data);
  EEPROM_write_8(Address>>8, Data>>8);
  }


А как вы определяете, что ничего не пишеться? Может все таки все нормально, и ваш метод контроля не работает smile.gif
singlskv
Цитата(smk @ Jan 31 2008, 00:08) *
был уровень оптимизации -О0. включил -О1. стала выполняться(на симуляторе). Что это было?
Это было невнимательное чтение даташита:
If the EEPMn bits are zero, writing EEPE (within four cycles after EEMPE is written) will trigger the
erase/write operation.


На -O0 Вам никто не гарантирует что будет <=4 цикла между:
EECR |= (1<<EEMPE);
EECR |= (1<<EEPE);
smk
Цитата
Если убрать эту явную ляпу

Точно по даташиту. Пишите в Атмел.
Цитата
На -O0 Вам никто не гарантирует что будет <=4 цикла между:

э... почему? как Вы узнали об этом?
Цитата
А как вы определяете, что ничего не пишеться?

По факту и при симуляции.
Цитата
Может все таки все нормально, и ваш метод контроля не работает

Да сложного ничего нет. Аналог программы, написанный в CVAVR, работает без сбоев.

Цитата
Ну и еще сложно вы функции пишете (правильно, но вычурно).

Спасибо, попробую.
singlskv
Цитата(smk @ Feb 4 2008, 23:34) *
э... почему? как Вы узнали об этом?
Потому что это стандартная ошибка...
Покажите Ваши листинги на -00 и на -O1
Ну и еще раз перечитайте мою цитату насчет 4 тактов...
smk
Цитата
Ну и еще раз перечитайте мою цитату насчет 4 тактов...

Перечитал. Только как гарантировано писать чтоб не более 4-х тактов?
singlskv
Цитата(smk @ Feb 5 2008, 00:31) *
Перечитал. Только как гарантировано писать чтоб не более 4-х тактов?

-Штирлиц, почему Вы всегда отвечаете вопросом на вопрос
- А разьве это плохо ?

А зачем вобще компилируете в -O0 ?
Вам кажется что так проще/правильнее отлаживать ?
Тогда Вы глубоко заблуждаетесь...

Гарантированно только с помощью библиотечных функций записи в EEPROM,
только я например не люблю пользоваться ими в принципе, ну не устраивают они меня и все тут...

Поэтому у меня всегда компилируется или на -O2 или на -Os,
ну и код в асме при этом как то более правильным/читаемым выглядит.
Baser
Цитата(smk @ Feb 4 2008, 22:34) *
Точно по даташиту. Пишите в Атмел.

Я тогда специально заглянул на сайт Атмела в даташит на Tiny24, поскольку конкретно её не применял. Там все как у меня laughing.gif
Но я уже написал, что это ничего не меняет, поскольку куда нуль не сдвигай, ничего не изменится smile.gif

А если все дело в 4-х тактах, то применяйте библиотечные функции. В gcc они есть в виде функций, в ИАРе в виде расширения __eeprom
Или другой вариант - напишите их на ассме и подключите к проекту.
smk
Цитата
Я тогда специально заглянул на сайт Атмела в даташит на Tiny24, поскольку конкретно её не применял. Там все как у меня

В варианте с Ассемблером - да, а на С - так как у меня.

Цитата
А если все дело в 4-х тактах, то применяйте библиотечные функции.

Я уже столкнулся с тем, что библиотеки WinAVR дают громоздкий код, мало того. При попытке разрешить прерывания глобально - встала вся программа. Так что пытаюсь писать сам. Для начала для маленьких Тини, потом для Мега, опираясь на опыт.
singlskv
Цитата(smk @ Feb 5 2008, 01:26) *
Я уже столкнулся с тем, что библиотеки WinAVR дают громоздкий код, мало того.
Правда ? Ну тогда предлагаю Вам для примера более оптимально написать
CRC16... например...
Цитата
При попытке разрешить прерывания глобально - встала вся программа. Так что пытаюсь писать сам. Для начала для маленьких Тини, потом для Мега, опираясь на опыт.
Вот только давайте без ерунды, WinAVR здесь явно ни при чем...
smk
Цитата
библиотеки WinAVR

прошу прощения, я имел ввиду AVRlib.
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.