44 #include <avr/interrupt.h>
45 #include <avr/pgmspace.h>
47 #include "dev/watchdog.h"
56 #define PRINTF(FORMAT,args...) printf_P(PSTR(FORMAT),##args)
63 #ifdef COFFEE_INGA_EEPROM
67 static const unsigned char nullb[COFFEE_SECTOR_SIZE];
73 avr_eeprom_erase(uint16_t sector)
76 (
unsigned char *) nullb,
sizeof (nullb));
80 #ifdef COFFEE_INGA_FLASH
90 uint32_t addr32 = COFFEE_START + addr;
91 uint16_t isize = size;
93 unsigned char *bufo = (
unsigned char *) buf;
95 uint16_t w = addr32 >> 1;
96 PRINTF(
"r0x%04x(%u) ", w, size);
98 #ifndef FLASH_WORD_READS
99 for (; isize > 0; isize--) {
100 #if FLASH_COMPLEMENT_DATA
101 *buf++ = ~(uint8_t) pgm_read_byte_far(addr32++);
103 *buf++ = (uint8_t) pgm_read_byte_far(addr32++);
109 #if FLASH_COMPLEMENT_DATA
110 *buf++ = ~(uint8_t) pgm_read_byte_far(addr32++);
112 *buf++ = (uint8_t) pgm_read_byte_far(addr32++);
116 for (; isize > 1; isize -= 2) {
117 #if FLASH_COMPLEMENT_DATA
118 *(uint16_t *) buf = ~(uint16_t) pgm_read_word_far(addr32);
120 *(uint16_t *) buf = (uint16_t) pgm_read_word_far(addr32);
126 #if FLASH_COMPLEMENT_DATA
127 *buf++ = ~(uint8_t) pgm_read_byte_far(addr32);
129 *buf++ = (uint8_t) pgm_read_byte_far(addr32);
148 avr_flash_erase(coffee_page_t sector)
152 #if FLASH_COMPLEMENT_DATA
154 volatile uint8_t sreg;
160 for (i = 0; i < COFFEE_SECTOR_SIZE / COFFEE_PAGE_SIZE; i++) {
161 for (addr32 = COFFEE_START + (((sector + i) * COFFEE_PAGE_SIZE)
162 & ~(COFFEE_PAGE_SIZE - 1)); addr32 < (COFFEE_START + (((sector
163 + i + 1) * COFFEE_PAGE_SIZE) & ~(COFFEE_PAGE_SIZE - 1))); addr32
165 boot_page_erase(addr32);
166 boot_spm_busy_wait();
174 for (i = 0; i < COFFEE_SECTOR_SIZE / COFFEE_PAGE_SIZE; i++) {
175 avr_flash_write((sector + i) * COFFEE_PAGE_SIZE, 0, 0);
192 uint8_t bb, ba, sreg;
202 #if 0 //this is 8 bytes longer
203 uint16_t startpage = addr / COFFEE_PAGE_SIZE;
204 addr32 = COFFEE_START + startpage*COFFEE_PAGE_SIZE;
206 addr32 = (COFFEE_ADDRESS&~(SPM_PAGESIZE - 1))+(addr&~(SPM_PAGESIZE - 1));
208 bb = addr & (SPM_PAGESIZE - 1);
209 ba = COFFEE_PAGE_SIZE - ((addr + size)&0xff);
212 uint16_t startpage = addr / COFFEE_PAGE_SIZE;
215 PRINTF(
"w0x%04x %u %u %u", w, size, bb, ba);
217 PRINTF(
"e0x%04x %u ", w, startpage);
223 if (size == 0)
return;
226 w = pgm_read_word_far(addr32);
227 boot_page_fill(addr32, w);
234 w = pgm_read_word_far(addr32);
235 #if FLASH_COMPLEMENT_DATA
245 #if FLASH_COMPLEMENT_DATA
248 boot_page_fill(addr32, w);
265 if ((addr32 & 0x000000ff) == 0) {
268 boot_page_erase(addr32);
269 boot_spm_busy_wait();
270 boot_page_write(addr32);
271 boot_spm_busy_wait();
278 w = pgm_read_word_far(addr32);
281 #if FLASH_COMPLEMENT_DATA
288 boot_page_fill(addr32, w);
294 #if FLASH_COMPLEMENT_DATA
295 addr32 += 2 * SPM_PAGESIZE;
297 for (w = 0; w < SPM_PAGESIZE; w++) {
298 boot_page_fill(addr32, 0);
305 boot_page_erase(addr32);
306 boot_spm_busy_wait();
307 #if FLASH_COMPLEMENT_DATA
309 boot_page_write(addr32);
310 boot_spm_busy_wait();
313 boot_page_write(addr32);
314 boot_spm_busy_wait();
330 #ifdef COFFEE_INGA_EXTERNAL
336 PRINTF(
"external_flash_write_page(page %u, offset %u, buf %p, size %u) \n", page, offset, buf, size);
342 if (page > COFFEE_PAGES) {
346 unsigned char buffer[COFFEE_PAGE_SIZE];
354 memcpy(buffer + offset, buf, size);
361 PRINTF(
"Page %u programmed with %u bytes (%u new)\n", page, COFFEE_PAGE_SIZE, size);
367 PRINTF(
">>>>> external_flash_write(addr %u, buf %p, size %u)\n", addr, buf, size);
369 if (addr > COFFEE_SIZE) {
374 coffee_page_t current_page = addr / COFFEE_PAGE_SIZE;
377 while (written < size) {
382 if (addr > page_start) {
384 offset = addr - page_start;
389 if (length > (COFFEE_PAGE_SIZE - offset)) {
390 length = COFFEE_PAGE_SIZE - offset;
393 external_flash_write_page(current_page, offset, buf + written, length);
401 for (g = 0; g < size; g++) {
402 printf(
"%02X %c ", buf[g] & 0xFF, buf[g] & 0xFF);
411 PRINTF(
"external_flash_read_page(page %u, offset %u, buf %p, size %u)\n", page, offset, buf, size);
413 if (page > COFFEE_PAGES) {
423 for (g = 0; g < size; g++) {
424 printf(
"%02X %c ", buf[g] & 0xFF, buf[g] & 0xFF);
433 PRINTF(
">>>>> external_flash_read(addr %u, buf %p, size %u)\n", addr, buf, size);
439 if (addr > COFFEE_SIZE) {
444 coffee_page_t current_page = addr / COFFEE_PAGE_SIZE;
447 while (read < size) {
452 if (addr > page_start) {
454 offset = addr - page_start;
459 if (length > (COFFEE_PAGE_SIZE - offset)) {
460 length = (COFFEE_PAGE_SIZE - offset);
463 external_flash_read_page(current_page, offset, buf + read, length);
474 for (g = 0; g < size; g++) {
475 printf(
"%02X %c ", buf[g] & 0xFF, buf[g] & 0xFF);
482 external_flash_erase(coffee_page_t page)
484 if (page > COFFEE_PAGES) {
488 PRINTF(
"external_flash_erase(page %u)\n", page);
519 #ifdef COFFEE_INGA_SDCARD
523 static uint8_t cfs_buffer[512];
528 PRINTF(
"sd_write_page(page %lu, offset %lu, buf %p, size %lu) \n", page, offset, buf, size);
534 if (page > COFFEE_PAGES) {
544 memcpy(cfs_buffer + offset, buf, size);
551 PRINTF(
"Page %lu programmed with %lu bytes (%lu new)\n", page, COFFEE_PAGE_SIZE, size);
557 PRINTF(
">>>>> sd_write(addr %lu, buf %p, size %lu)\n", addr, buf, size);
559 if (addr > COFFEE_SIZE) {
564 coffee_page_t current_page = addr / COFFEE_PAGE_SIZE;
567 while (written < size) {
572 if (addr > page_start) {
574 offset = addr - page_start;
579 if (length > (COFFEE_PAGE_SIZE - offset)) {
580 length = COFFEE_PAGE_SIZE - offset;
583 sd_write_page(current_page, offset, buf + written, length);
591 for (g = 0; g < size; g++) {
592 printf(
"%02X ", buf[g] & 0xFF, buf[g] & 0xFF);
601 PRINTF(
"sd_read_page(page %lu, offset %lu, buf %p, size %lu)\n", page, offset, buf, size);
603 if (page > COFFEE_PAGES) {
608 memcpy(buf, cfs_buffer + offset, size);
613 for (g = 0; g < size; g++) {
614 printf(
"%02X ", buf[g] & 0xFF, buf[g] & 0xFF);
624 PRINTF(
">>>>> sd_read(addr %lu, buf %p, size %lu)\n", addr, buf, size);
630 if (addr > COFFEE_SIZE) {
635 coffee_page_t current_page = addr / COFFEE_PAGE_SIZE;
638 while (read < size) {
643 if (addr > page_start) {
645 offset = addr - page_start;
650 if (length > (COFFEE_PAGE_SIZE - offset)) {
651 length = (COFFEE_PAGE_SIZE - offset);
654 sd_read_page(current_page, offset, buf + read, length);
656 PRINTF(
"Page %lu read with %lu bytes (offset %lu)\n", current_page, length, offset);
665 for (g = 0; g < size; g++) {
666 printf(
"%02X ", buf[g] & 0xFF, buf[g] & 0xFF);
673 sd_erase(coffee_page_t page)
675 if (page > COFFEE_PAGES) {
679 PRINTF(
"sd_erase(page %lu)\n", page);
680 memset(cfs_buffer, 0, 512);