AVR Eeprom的理解
AVR Eeprom Understanding
我已经开始创建一个按钮计数器并成功地做到了然后我转向读写 eeprom 我尝试使用 eeprom 读写单个字节并且也成功地这样做了,漂亮基本的东西。最近我尝试使用 eeprom_update_word
函数,这让我有点困惑,因为我认为效果不太好我已经尝试过但成功了有人可以帮助我吗?下面是我写的:
// removed the standard header as they aren't displayed here!
void lcd_num (int);
int main(void)
{
uint16_t c = 0;
DDRD = 0x00;
lcd_init(LCD_DISP_ON);
lcd_string(5, 0, "COUNTER");
lcd_command(0xC5);
// check if value has already been used/initialized...
if (eeprom_read_word((uint16_t*)10) == UINT16_MAX)
{
// ...if not, init to 0
eeprom_write_word((uint16_t*)10 , 0);
}
else
{
// ...if yes, read value back
c = eeprom_read_word((uint16_t*)10);
}
lcd_data(c+48);
while(1)
{
if( (PIND & 0x01) == 1 )
{
c++;
lcd_command(0xC5);
lcd_num(c);
eeprom_update_word((uint16_t*)10, c);
while( (PIND & 0x01) == 1 );
}
if((PIND & 0x02) == 1)
{
eeprom_write_word((uint16_t*)10,0);
c = eeprom_read_word((uint16_t*)10);
while((PIND & 0x02) == 1);
}
}
}
void lcd_num(int n){
lcd_data((n/1000)+48);
n %= 1000;
lcd_data((n/100)+48);
n %= 100;
lcd_data((n/10)+48);
n %= 10;
lcd_data(n+48);
}
void lcd_num(int n){
lcd_data((n/1000)+48);
n %= 1000;
lcd_data((n/100)+48);
n %= 100;
lcd_data((n/10)+48);
n %= 10;
lcd_data(n+48);
}
我可以在这里再请一个忙吗?我想使用手动按钮擦除 eeprom,这样我就不会 运行 超出 space 我试过了,但这不起作用。我这样做正确吗??
由于您的程序 所有 都是在开机时执行的,因此这些行也将 运行:
uint16_t c = 0;
// unrelated lines ...
eeprom_write_word((uint16_t*)10 ,c);
并且它们会覆盖您之前存储在那里的值。
目前,您的计数器值会在每次重新启动时被覆盖。您需要做一些检查,EEPROM 位置是否已经初始化(默认 EEPROM 内容全部为 0xFF)。
// check if value has already been used/initialized...
if (eeprom_read_word((uint16_t*)10) == UINT16_MAX)
{
// ...if not, init to 0
eeprom_write_word((uint16_t*)10 , 0);
}
else
{
// ...if yes, read value back
c = eeprom_read_word((uint16_t*)10);
}
我已经开始创建一个按钮计数器并成功地做到了然后我转向读写 eeprom 我尝试使用 eeprom 读写单个字节并且也成功地这样做了,漂亮基本的东西。最近我尝试使用 eeprom_update_word
函数,这让我有点困惑,因为我认为效果不太好我已经尝试过但成功了有人可以帮助我吗?下面是我写的:
// removed the standard header as they aren't displayed here!
void lcd_num (int);
int main(void)
{
uint16_t c = 0;
DDRD = 0x00;
lcd_init(LCD_DISP_ON);
lcd_string(5, 0, "COUNTER");
lcd_command(0xC5);
// check if value has already been used/initialized...
if (eeprom_read_word((uint16_t*)10) == UINT16_MAX)
{
// ...if not, init to 0
eeprom_write_word((uint16_t*)10 , 0);
}
else
{
// ...if yes, read value back
c = eeprom_read_word((uint16_t*)10);
}
lcd_data(c+48);
while(1)
{
if( (PIND & 0x01) == 1 )
{
c++;
lcd_command(0xC5);
lcd_num(c);
eeprom_update_word((uint16_t*)10, c);
while( (PIND & 0x01) == 1 );
}
if((PIND & 0x02) == 1)
{
eeprom_write_word((uint16_t*)10,0);
c = eeprom_read_word((uint16_t*)10);
while((PIND & 0x02) == 1);
}
}
}
void lcd_num(int n){
lcd_data((n/1000)+48);
n %= 1000;
lcd_data((n/100)+48);
n %= 100;
lcd_data((n/10)+48);
n %= 10;
lcd_data(n+48);
}
void lcd_num(int n){
lcd_data((n/1000)+48);
n %= 1000;
lcd_data((n/100)+48);
n %= 100;
lcd_data((n/10)+48);
n %= 10;
lcd_data(n+48);
}
我可以在这里再请一个忙吗?我想使用手动按钮擦除 eeprom,这样我就不会 运行 超出 space 我试过了,但这不起作用。我这样做正确吗??
由于您的程序 所有 都是在开机时执行的,因此这些行也将 运行:
uint16_t c = 0;
// unrelated lines ...
eeprom_write_word((uint16_t*)10 ,c);
并且它们会覆盖您之前存储在那里的值。
目前,您的计数器值会在每次重新启动时被覆盖。您需要做一些检查,EEPROM 位置是否已经初始化(默认 EEPROM 内容全部为 0xFF)。
// check if value has already been used/initialized...
if (eeprom_read_word((uint16_t*)10) == UINT16_MAX)
{
// ...if not, init to 0
eeprom_write_word((uint16_t*)10 , 0);
}
else
{
// ...if yes, read value back
c = eeprom_read_word((uint16_t*)10);
}