/////////////////////////////////////////////////////////////////////////
//
// KNIHOVNA PRO PRACI S EXTERNI PAMETI EEPROM RADY 24XX (I2C SBERNICE)
//
/////////////////////////////////////////////////////////////////////////
//
// PEFI S.ICZ a.s. 2003
//
// Verze 1.0 - uvodni verze
// POZN: podpora HW adresy neni vyzkousena, nebyla k dispozici takova soucastka
//
/////////////////////////////////////////////////////////////////////////
//
// funkce:
// ExtEE_init()
// - inicializuje porty a pripadne HW i2c jednotku
//
// ExtEE_write_byte(int16 adr,int8 data)
// - zapise bajt na adresu
//
// ExtEE_write_array(int16 adr,int8 *data, int8 Len)
// - zapise pole bajtu delky Len od adresy adr
//
// int8 ExtEE_read_byte(int16 adr)
// - precte bajt z adresy adr
//
// int8 ExtEE_read_byte_inc()
// - precte bajt z adresy nasledujici po adrese posledni operace a inkrementuje ji
// - funguje jen v ramci jedne stranky
//
// ExtEE_read_array(int16 adr,int8 *data, int8 Len)
// - precte pole bajtu delky Len od adresy adr
//
// definice a prepinace
// #define EXTEE_SDA /* pin, na kterem je pripojen signal SDA */
// #define EXTEE_SCL /* pin, na kterem je pripojen signal SCL */
// #define EXTEE_WRITE_BURST /* pocet bajtu, ktere lze zapsat do pameti naraz */
// #define EXTEE_PAGE_CTRL /* zapne(1) / vypne(0) podporu strankovani */
// #define EXT_EE_HW_ADR /* nastavi a zapne podporu hw adresy I2C zarizeni */
// #define EXTEE_HW /* zapne(1) / vypne(0) HW podporu i2c */
// POZN: Vypnuti podpory strankvani prodlouzi funkci ExtEE_write_array o cca 20 slov, ovsem
// potom je treba hlidat vztah mezi adresou a delkou zapisovaneho pole. Lze zapsat max. EXTEE_WRITE_BURST bajtu
// a to pocinaje adresou v nasobcich EXTEE_WRITE_BURST (0x,1x,2x...). Pokud nezapiseme cely burst a budeme priste pokracovat
// nasledujici adresou, lze zapsat jen cast do EXTEE_WRITE_BURST. Zbytek lze zapsat novym burstem. Opet max. EXTEE_WRITE_BURST bajtu
// Podporu EXTEE_HW lze zapnout u procesoru, ktere tuto jednotku maji.
//
//
// defaultni definice
//
#ifndef EXTEE_SDA
#define EXTEE_SDA PIN_C4
#define EXTEE_SCL PIN_C3
#endif
#ifndef EXTEE_WRITE_BURST
#define EXTEE_WRITE_BURST 16 /* pocet bajtu, ktere lze zapsat naraz */
#endif
#ifndef EXTEE_PAGE_CTRL
#define EXTEE_PAGE_CTRL 1 /* podpora stranokvani zapnuta */
#endif
#ifndef EXTEE_HW
#define EXTEE_HW 0 /* HW podpora i2c vypnuta */
#endif
/****************************************************************************************************/
// Privatni sekce, cist jen v pripade, ze neco nefunguje
/****************************************************************************************************/
// nastaveni podpory I2C sbernice
#if EXTEE_HW != 0
#use i2c(master,sda=EXTEE_SDA,scl=EXTEE_SCL,FORCE_HW)
#else
#use i2c(master,sda=EXTEE_SDA,scl=EXTEE_SCL)
#endif
//////////////////////////////////////////////////////////
///// FUNKCE pro inicializaci
//////////////////////////////////////////////////////////
// inicializuje port
//
void ExtEE_init() {
output_float(EXTEE_SCL);
output_float(EXTEE_sda);
#ifdef EEPROM_HW
// zapne SSP jednotku, #use i2c to neudela, asi chyba v cecku
#ASM
BSF SSPCON._SSPEN // BSF 0x14.5
BSF SSPCON._SSPM3 // BSF 0x14.3
#endasm
#endif
}
////////////////////////////////
/// FUNKCE PRO ZAPIS
///////////////////////////////
// zapise bajt do eeprom
//
void ExtEE_write_byte(int16 adr, int8 data) {
#ifdef EXTEE_HW_ADR
do
i2c_start();
while (i2c_write((0xa0|((EXTEE_HW_ADR<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
i2c_write(make8(adr,1)); // posli vyssi cast adresy
#else
do
i2c_start();
while (i2c_write((0xa0|((make8(adr,1)<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
#endif
// i2c_write(make8(adr,0)); //je o 1 slovo delsi a asi vice koser
i2c_write(adr);
i2c_write(data);
i2c_stop();
}
#if EXTEE_PAGE_CTRL != 0
// zapise pole bajtu do eeprom, varianta s kontolou strankovani
//
void ExtEE_write_array(int16 adr, int8 *data, int8 Len) {
int8 burst;
while(len!=0)
{
burst=(EXTEE_WRITE_BURST-1)-(make8(adr,0)&(EXTEE_WRITE_BURST-1))+1; // pocet bajtu, ktere lze naraz zapsat
if(burst>len) burst=len; // zapiseme zbytek
len=len-burst;
// navazani spojeni a zapis adresy
#ifdef EXTEE_HW_ADR
do
i2c_start();
while (i2c_write((0xa0|((EXTEE_HW_ADR<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
i2c_write(make8(adr,1)); // posli vyssi cast adresy
#else
do
i2c_start();
while(i2c_write((0xa0|((make8(adr,1)<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
#endif
i2c_write(adr);
adr+=burst; // adresu posun na zacatek dalsiho burstu
// poslani burstu bajtu
do
i2c_write(*Data++);
while (--burst);
i2c_stop();
}
}
#else
// zapise pole bajtu do eeprom, varianta bez kontroly strankovani, je o 21 slov kratsi
//
void ExtEE_write_array(int16 adr, int8 *data, int8 Len) {
// navazani spojeni a zapis adresy
#ifdef EXTEE_HW_ADR
do
i2c_start();
while (i2c_write((0xa0|((EXTEE_HW_ADR<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
i2c_write(make8(adr,1)); // posli vyssi cast adresy
#else
do
i2c_start();
while(i2c_write((0xa0|((make8(adr,1)<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
#endif
i2c_write(adr);
// poslani burstu bajtu
do
i2c_write(*Data++);
while (--len);
i2c_stop();
}
#endif
////////////////////////////////
/// FUNKCE PRO CTENI
///////////////////////////////
// precte bajt z eeprom
//
int8 ExtEE_read_byte(int16 adr) {
int8 data;
#ifdef EXTEE_HW_ADR
do
i2c_start();
while (i2c_write((0xa0|((EXTEE_HW_ADR<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
i2c_write(make8(adr,1)); // posli vyssi cast adresy
#else
do
i2c_start();
while(i2c_write((0xa0|((make8(adr,1)<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
#endif
i2c_write(adr);
i2c_start();
#ifdef EXTEE_HW_ADR
i2c_write((0xa0|((EXTEE_HW_ADR<<1)&0x0f))|1);
#else
i2c_write((0xa0|((make8(adr,1)<<1)&0x0f))|1);
#endif
data=i2c_read(0);
i2c_stop();
return(data);
}
// precte bajt z eeprom z posledni adresy+1 a adresu inkrementuje, funguje jen v ramci jedne stranky
//
int8 ExtEE_read_byte_inc() {
int8 data;
i2c_start();
#ifdef EXTEE_HW_ADR
i2c_write((0xa0|((EXTEE_HW_ADR<<1)&0x0f))|1);
#else
i2c_write(0xa1);
#endif
data=i2c_read(0);
i2c_stop();
return(data);
}
// precte pole bajtu z eeprom
//
void ExtEE_read_array(int16 adr, int8 *Data, int8 Len) {
#ifdef EXTEE_HW_ADR
do
i2c_start();
while (i2c_write((0xa0|((EXTEE_HW_ADR<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
i2c_write(make8(adr,1)); // posli vyssi cast adresy
#else
do
i2c_start();
while(i2c_write((0xa0|((make8(adr,1)<<1)&0x0f))&0xfe)); // zkousej dal pokud je pamet zaneprazdnena
#endif
i2c_write(adr);
i2c_start();
#ifdef EXTEE_HW_ADR
i2c_write((0xa0|((EXTEE_HW_ADR<<1)&0x0f))&0xfe); // zkousej dal pokud je pamet zaneprazdnena
#else
i2c_write((0xa0|((make8(adr,1)<<1)&0x0f))|1);
#endif
Len--; // posledni bajt se cte zvlast, nema ACK
do
*(Data++)=i2c_read(1);
while (--Len);
*(data++)=i2c_read(0); // u posledniho bajtu neni ACK
i2c_stop();
}
// End of File
|