1 /***************************************************************************
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
10 * Copyright (C) 2006 by Miika Pekkarinen
12 * This program is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU General Public License
14 * as published by the Free Software Foundation; either version 2
15 * of the License, or (at your option) any later version.
17 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
18 * KIND, either express or implied.
20 ****************************************************************************/
28 #include "eeprom_24cxx.h"
30 /* Use cache to speedup writing to the chip. */
31 static char data_cache
[EEPROM_SIZE
];
32 static uint8_t cached_bitfield
[EEPROM_SIZE
/8];
34 #define IS_CACHED(addr) (cached_bitfield[addr/8] & (1 << (addr % 8)))
35 #define SET_CACHED(addr) (cached_bitfield[addr/8] |= 1 << (addr % 8))
37 void eeprom_24cxx_init(void)
40 memset(cached_bitfield
, 0, sizeof cached_bitfield
);
43 static int eeprom_24cxx_read_byte(unsigned int address
, char *c
)
49 if (address
>= EEPROM_SIZE
)
51 logf("EEPROM address: %d", address
);
55 /* Check from cache. */
56 if (IS_CACHED(address
))
58 logf("EEPROM RCached: %d", address
);
59 *c
= data_cache
[address
];
66 ret
= sw_i2c_read(EEPROM_ADDR
, address
, &byte
, 1);
67 } while (ret
< 0 && count
++ < 200);
71 logf("EEPROM RFail: %d/%d/%d", ret
, address
, count
);
77 /* keep between {} as logf is whitespace in normal builds */
78 logf("EEPROM rOK: %d retries", count
);
82 data_cache
[address
] = byte
;
89 static int eeprom_24cxx_write_byte(unsigned int address
, char c
)
94 if (address
>= EEPROM_SIZE
)
96 logf("EEPROM address: %d", address
);
100 /* Check from cache. */
101 if (IS_CACHED(address
) && data_cache
[address
] == c
)
103 logf("EEPROM WCached: %d", address
);
109 ret
= sw_i2c_write(EEPROM_ADDR
, address
, &c
, 1);
110 } while (ret
< 0 && count
++ < 200) ;
114 logf("EEPROM WFail: %d/%d", ret
, address
);
120 /* keep between {} as logf is whitespace in normal builds */
121 logf("EEPROM wOK: %d retries", count
);
125 data_cache
[address
] = c
;
130 int eeprom_24cxx_read(unsigned char address
, void *dest
, int length
)
132 char *buf
= (char *)dest
;
136 for (i
= 0; i
< length
; i
++)
138 ret
= eeprom_24cxx_read_byte(address
+i
, &buf
[i
]);
146 int eeprom_24cxx_write(unsigned char address
, const void *src
, int length
)
148 const char *buf
= (const char *)src
;
151 for (i
= 0; i
< length
; i
++)
153 if (eeprom_24cxx_write_byte(address
+i
, buf
[i
]) < 0)