a bit of code cleanup.. use a single function to get the statusbar height (or lack...
[Rockbox.git] / firmware / drivers / eeprom_24cxx.c
bloba0d8f83eb72cc584d0db24ce5c4e3b0f8f3c25cf
1 /***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
10 * Copyright (C) 2006 by Miika Pekkarinen
12 * All files in this archive are subject to the GNU General Public License.
13 * See the file COPYING in the source tree root for full license agreement.
15 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
16 * KIND, either express or implied.
18 ****************************************************************************/
20 #include "logf.h"
21 #include "string.h"
22 #include "inttypes.h"
24 #include "sw_i2c.h"
26 #include "eeprom_24cxx.h"
28 /* Use cache to speedup writing to the chip. */
29 static char data_cache[EEPROM_SIZE];
30 static uint8_t cached_bitfield[EEPROM_SIZE/8];
32 #define IS_CACHED(addr) (cached_bitfield[addr/8] & (1 << (addr % 8)))
33 #define SET_CACHED(addr) (cached_bitfield[addr/8] |= 1 << (addr % 8))
35 void eeprom_24cxx_init(void)
37 sw_i2c_init();
38 memset(cached_bitfield, 0, sizeof cached_bitfield);
41 int eeprom_24cxx_read_byte(unsigned int address, char *c)
43 int ret;
44 char byte;
45 int count = 0;
47 if (address >= EEPROM_SIZE)
49 logf("EEPROM address: %d", address);
50 return -9;
53 /* Check from cache. */
54 if (IS_CACHED(address))
56 logf("EEPROM RCached: %d", address);
57 *c = data_cache[address];
58 return 0;
61 *c = 0;
64 ret = sw_i2c_read(EEPROM_ADDR, address, &byte, 1);
65 } while (ret < 0 && count++ < 200);
67 if (ret < 0)
69 logf("EEPROM RFail: %d/%d/%d", ret, address, count);
70 return ret;
73 if (count)
75 /* keep between {} as logf is whitespace in normal builds */
76 logf("EEPROM rOK: %d retries", count);
79 /* Cache the byte. */
80 data_cache[address] = byte;
81 SET_CACHED(address);
83 *c = byte;
84 return 0;
87 int eeprom_24cxx_write_byte(unsigned int address, char c)
89 int ret;
90 int count = 0;
92 if (address >= EEPROM_SIZE)
94 logf("EEPROM address: %d", address);
95 return -9;
98 /* Check from cache. */
99 if (IS_CACHED(address) && data_cache[address] == c)
101 logf("EEPROM WCached: %d", address);
102 return 0;
107 ret = sw_i2c_write(EEPROM_ADDR, address, &c, 1);
108 } while (ret < 0 && count++ < 200) ;
110 if (ret < 0)
112 logf("EEPROM WFail: %d/%d", ret, address);
113 return ret;
116 if (count)
118 /* keep between {} as logf is whitespace in normal builds */
119 logf("EEPROM wOK: %d retries", count);
122 SET_CACHED(address);
123 data_cache[address] = c;
125 return 0;
128 int eeprom_24cxx_read(unsigned char address, void *dest, int length)
130 char *buf = (char *)dest;
131 int ret = 0;
132 int i;
134 for (i = 0; i < length; i++)
136 ret = eeprom_24cxx_read_byte(address+i, &buf[i]);
137 if (ret < 0)
138 return ret;
141 return ret;
144 int eeprom_24cxx_write(unsigned char address, const void *src, int length)
146 const char *buf = (const char *)src;
147 int i;
149 for (i = 0; i < length; i++)
151 if (eeprom_24cxx_write_byte(address+i, buf[i]) < 0)
152 return -1;
155 return 0;