📄 avrreadeeprom.c
字号:
#include <inttypes.h>
#include <stdio.h>
#include <stdlib.h>
#include <avr/io.h>
#include <util/twi.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#define DEBUG 1
#define F_CPU 14745600UL
#ifndef UCSRB
# ifdef UCSR1A /* ATmega128 */
# define UCSRA UCSR1A
# define UCSRB UCSR1B
# define UBRR UBRR1L
# define UDR UDR1
# else /* ATmega8 */
# define UCSRA USR
# define UCSRB UCR
# endif
#endif
#ifndef UBRR
# define UBRR UBRRL
#endif
#define TWI_SLA_24CXX 0xa2
#define MAX_ITER 200
#define PAGE_SIZE 8
uint8_t twst;
unsigned char k;
ioinit(void)
{
#if F_CPU <= 1000000UL
UCSRA = _BV(U2X);
UBRR = (F_CPU / (8 * 9600UL)) - 1; /* 9600 Bd */
#else
UBRR = (F_CPU / (16 * 9600UL)) - 1; /* 9600 Bd */
#endif
UCSRB = _BV(TXEN); /* tx enable */
/* initialize TWI clock: 100 kHz clock, TWPS = 0 => prescaler = 1 */
#if defined(TWPS0)
/* has prescaler (mega128 & newer) */
TWSR = 0;
#endif
#if F_CPU < 3600000UL
TWBR = 10; /* smallest TWBR value*/
#else
TWBR = (F_CPU / 100000UL - 16) / 2;
#endif
}
/*
* Send character c down the UART Tx, wait until tx holding register
* is empty.
*/
int uart_putchar(char c, FILE *unused)
{
if (c == '\n')
uart_putchar('\r', 0);
loop_until_bit_is_set(UCSRA, UDRE);
UDR = c;
return 0;
}
void delay(unsigned int ms)
{
_delay_ms(ms);
}
int IICRead_Byte( uint16_t eeaddr, int len, uint8_t *buf)
{
uint8_t sla, twcr, n = 0;
int rv = 0;
/*high byte of eeprom*/
sla =TWI_SLA_24CXX| (((eeaddr >> 8) & 0x07) << 1);
restart:
if (n++ >= MAX_ITER)/* error limte*/
return -1;
/*******************************************/
/* master transmitter mode */
begin:
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); /* send start condition */
while ((TWCR & _BV(TWINT)) == 0) ;
twst=TW_STATUS;
if( twst!= TW_START)
{
return -1;
}
delay(5);
/* send SLA+W */
TWDR = sla | TW_WRITE;
TWCR = _BV(TWINT) | _BV(TWEN); /* start transmission */
while ((TWCR & _BV(TWINT)) == 0) ; /* wait for transmission */
twst=TW_STATUS;
if(twst!=TW_MT_SLA_ACK)
{
return -1;
}
delay(10);
TWDR = eeaddr; /* low 8 bits of addr */
TWCR = _BV(TWINT) | _BV(TWEN); /* start transmission */
while ((TWCR & _BV(TWINT)) == 0) ; /* wait for transmission */
twst=TW_STATUS;
if(twst!=TW_MT_DATA_ACK)
{
return -1;
}
delay(10);
/* * master receiver mode*/
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); /* rstart condition */
while ((TWCR & _BV(TWINT)) == 0) ; /* wait for transmission */
twst=TW_STATUS;
if(twst!=TW_REP_START)
{
TWCR = _BV(TWINT) | _BV(TWSTO) | _BV(TWEN); /* send stop condition */
goto restart;
return -1;
}
PORTB=0X7F;
delay(10);
/* send SLA+R */
TWDR =sla| TW_READ;
/*TWDR= 1;*/
TWCR = _BV(TWINT) | _BV(TWEN); /* clear interrupt to start transmission */
delay(10);
while ((TWCR & _BV(TWINT)) == 0) ; /* wait for transmission */
_delay_us(1);
//TWCR=_BV(TWEA);
twst=TW_STATUS;
PORTB=0XBF;
if(twst!=TW_MR_SLA_ACK)
{
return -1;
}
for (twcr = _BV(TWINT) | _BV(TWEN) | _BV(TWEA);
len > 0;
len--)
{
if (len == 1)
{
twcr = _BV(TWINT) | _BV(TWEN); /* send NAK this time */
}
TWCR = twcr; /* clear int to start transmission */
while ((TWCR & _BV(TWINT)) == 0) ; /* wait for transmission */
switch ((twst = TW_STATUS))
{
case TW_MR_DATA_NACK:
len = 0; /* force end of loop */
case TW_MR_DATA_ACK:
*buf++ = TWDR;
rv++;
break;
default:
goto error;
}
}
quit:
TWCR = _BV(TWINT) | _BV(TWSTO) | _BV(TWEN); /* send stop condition */
return rv;
error:
rv = -1;
goto quit;
}
/*
* adr: eerpom address
* len: length (not use)
* a: data
*/
int IICWrite_Byte(uint16_t adr, int len, uint8_t a)
{
uint8_t sla, n = 0;
int rv = 0;
uint16_t endaddr;
DDRB=0XFF;
if (adr + len < (adr | (PAGE_SIZE - 1)))
endaddr = adr + len;
else
endaddr = (adr | (PAGE_SIZE - 1)) + 1;
len = endaddr - adr;
/* patch high bits of EEPROM address into SLA */
sla = TWI_SLA_24CXX | (((adr >> 8) & 0x07) << 1);
restart:
if (n++ >= MAX_ITER)
return -1;
begin:
TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); /*start */
while ((TWCR & _BV(TWINT)) == 0);
twst=TW_STATUS;
if(twst!=TW_START)
{
return -1;
}
TWDR = sla | TW_WRITE;/* send SLA+W */
TWCR = _BV(TWINT) | _BV(TWEN);
while ((TWCR & _BV(TWINT)) == 0) ;
twst=TW_STATUS;
if(twst!=TW_MT_SLA_ACK)
{
return -1;
}
TWDR = adr; /* low 8 bits of addr */
TWCR = _BV(TWINT) | _BV(TWEN); /* start transmission */
while ((TWCR & _BV(TWINT)) == 0) ;
twst=TW_STATUS;
if(twst!=TW_MT_DATA_ACK)
{
return -1;
}
/************************************/
TWDR= a; /*data*/
TWCR= _BV(TWINT)|_BV(TWEN);
while((TWCR & _BV(TWINT))==0);
twst=TW_STATUS;
if(twst!=TW_MT_DATA_ACK)
{
return -1;
}
quit:
TWCR = _BV(TWINT) | _BV(TWSTO) | _BV(TWEN); /* stop */
return 1;
error:
rv = -1;
goto quit;
}
FILE mystdout = FDEV_SETUP_STREAM(uart_putchar, NULL, _FDEV_SETUP_WRITE);
void
main(void)
{
uint16_t a;
int rv=0;
uint8_t b[200];
uint8_t x;
unsigned char address;
address=95;
ioinit();
delay (20);
_delay_ms(27890);
DDRB=0XFF;
k=0;
int i=0;
/*IICWrite_Byte(0,10,0);*/
//rv=IICWrite_Byte(0x25,1,0x34);
//;
while(1)
{
for(i=0;i<200;i++)
{
b[i]=i;
}
for(i=0;i<140;i++)
{
//rv=IICRead_Byte(0X00,40,&b);
rv=IICWrite_Byte(i,1,b[i]);
_delay_ms(50);
}
//rv=IICWrite_Byte(0x25,1,0x34);
_delay_ms(200000);
rv=IICRead_Byte(0,14,&b);
_delay_ms(200000);
}
/*
while(1)
{
_delay_ms(1000);
if(PIND&(1<<3))
{
_delay_ms(10);
//loop_until_bit_is_set(PIND,3);
//
PORTB=0xff;
}
else
{
_delay_ms(10);
rv=IICRead_Byte(address,10,&b);
PORTB=0;
_delay_ms(70000);
//address++;
}
}
*/
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -