[Tinyos-beta-commits]
CVS: tinyos-1.x/beta/AT45DB BlockRead.nc, NONE,
1.1 BlockStorage.h, NONE, 1.1 BlockStorageC.nc, NONE,
1.1 BlockStorageM.nc, NONE, 1.1 BlockWrite.nc, NONE,
1.1 FlashVolume.h, NONE, 1.1 FlashVolume.nc, NONE,
1.1 FlashVolumeC.nc, NONE, 1.1 FlashVolumeM.nc, NONE,
1.1 HALAT45DB.h, NONE, 1.1 HALAT45DB.nc, NONE,
1.1 HALAT45DBC.nc, NONE, 1.1 HALAT45DBM.nc, NONE,
1.1 HPLAT45DB.h, NONE, 1.1 HPLAT45DB.nc, NONE,
1.1 HPLAT45DBByte.nc, NONE, 1.1 PageEEPROMC.nc, NONE, 1.1
David Gay
idgay at users.sourceforge.net
Fri Jan 21 16:26:34 PST 2005
Update of /cvsroot/tinyos/tinyos-1.x/beta/AT45DB
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv10862
Added Files:
BlockRead.nc BlockStorage.h BlockStorageC.nc BlockStorageM.nc
BlockWrite.nc FlashVolume.h FlashVolume.nc FlashVolumeC.nc
FlashVolumeM.nc HALAT45DB.h HALAT45DB.nc HALAT45DBC.nc
HALAT45DBM.nc HPLAT45DB.h HPLAT45DB.nc HPLAT45DBByte.nc
PageEEPROMC.nc
Log Message:
a start on the new storage for the Atmel dataflash. In progress state
(status: the new HAL works as a replacement for PageEEPROMC).
--- NEW FILE: BlockRead.nc ---
// $Id: BlockRead.nc,v 1.1 2005/01/22 00:26:30 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
*/
includes BlockStorage;
interface BlockRead {
command result_t read(block_addr_t addr, uint8_t* buf, block_addr_t len);
event result_t readDone(result_t result);
command result_t verify();
event result_t verifyDone(result_t result);
command result_t computeCrc(block_addr_t addr, block_addr_t len);
event result_t computeCrcDone(result_t result, uint16_t crc);
}
--- NEW FILE: BlockStorage.h ---
// $Id: BlockStorage.h,v 1.1 2005/01/22 00:26:30 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
*/
#ifndef __BLOCK_STORAGE_H__
#define __BLOCK_STORAGE_H__
typedef uint16_t block_addr_t;
#endif
--- NEW FILE: BlockStorageC.nc ---
// $Id: BlockStorageC.nc,v 1.1 2005/01/22 00:26:30 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
*/
includes BlockStorage;
includes STM25P;
configuration BlockStorageC {
provides {
interface StdControl;
interface BlockWrite[uint8_t id];
interface BlockRead[uint8_t id];
}
}
implementation {
components
BlockStorageM,
FlashVolumeC,
PageEEPROMC,
LedsC as Leds;
StdControl = BlockStorageM;
StdControl = FlashVolumeC;
StdControl = PageEEPROMC;
BlockWrite = BlockStorageM;
BlockRead = BlockStorageM;
BlockStorageM.ActualFV -> FlashVolumeC.FlashVolume;
BlockStorageM.Leds -> Leds;
BlockStorageM.PageEEPROM -> PageEEPROMC;
}
--- NEW FILE: BlockStorageM.nc ---
// $Id: BlockStorageM.nc,v 1.1 2005/01/22 00:26:30 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
* @author: David Gay <dgay at acm.org>
*/
module BlockStorageM {
provides {
interface StdControl;
interface BlockWrite[uint8_t id];
interface BlockRead[uint8_t id];
}
uses {
interface FlashVolume as ActualFV[uint8_t id];
interface Leds;
interface PageEEPROM as HALAT45DB;
}
}
implementation
{
enum {
S_IDLE,
S_WRITE,
S_ERASE,
S_COMMIT,
S_READ,
S_VERIFY,
S_CRC,
};
uint8_t state;
uint8_t client;
uint8_t* bufPtr;
block_addr_t curAddr;
block_addr_t bytesRemaining;
uint16_t crc;
command result_t StdControl.init() {
state = S_IDLE;
return SUCCESS;
}
command result_t StdControl.start() {
return SUCCESS;
}
command result_t StdControl.stop() {
return SUCCESS;
}
result_t actualSignal(result_t result) {
uint8_t tmpState = state;
state = S_IDLE;
switch(tmpState)
{
case S_READ: return signal BlockRead.readDone[client](result);
case S_WRITE: return signal BlockWrite.writeDone[client](result);
case S_ERASE: return signal BlockWrite.eraseDone[client](result);
case S_CRC: return signal BlockRead.computeCrcDone[client](result, crc);
}
return SUCCESS;
}
task void signalSuccess() { actualSignal(SUCCESS); }
task void signalFail() { actualSignal(FAIL); }
void signalDone(result_t result) {
if (result == SUCCESS)
post signalSuccess();
else
post signalFail();
}
bool admitRequest(uint8_t newState, uint8_t id) {
if (state != S_IDLE)
return FALSE;
client = id;
state = newState;
return TRUE;
}
void calcRequest(block_addr_t addr, at45page_t *page,
at45pageoffset_t *offset, at45pageoffset_t *count) {
storage_addr_t physicalAddr = call ActualFV.physicalAddr[client](addr);
*page = physicalAddr >> AT45_PAGE_SIZE_LOG2;
*offset = physicalAddr & ((1 << AT45_PAGE_SIZE_LOG2) - 1);
if (bytesRemaining < (1 << AT45_PAGE_SIZE_LOG2) - *offset)
*count = bytesRemaining;
else
*count = (1 << AT45_PAGE_SIZE_LOG2) - *offset;
}
void continueRequest() {
at45page_t page;
at45pageoffset_t offset, count;
uint8_t *buf = bufPtr;
calcRequest(curAddr, &page, &offset, &count);
bytesRemaining -= count;
curAddr += count;
bufPtr += count;
switch (state)
{
case S_WRITE:
if (!call HALAT45DB.write(page, offset, buf, count))
post signalFail();
break;
case S_READ:
if (!call HALAT45DB.read(page, offset, buf, count))
post signalFail();
break;
case S_CRC:
if (!call HALAT45DB.computeCrc(page, offset, count, crc))
post signalFail();
break;
}
}
void newRequest(uint8_t newState, uint8_t id,
block_addr_t addr, uint8_t* buf, block_addr_t len) {
if (admitRequest(newState, id) == FAIL)
return FAIL;
curAddr = addr;
bufPtr = buf;
bytesRemaining = len;
continueRequest();
return SUCCESS;
}
command result_t BlockWrite.write[uint8_t id](block_addr_t addr, uint8_t* buf, block_addr_t len) {
return newRequest(S_WRITE, addr, buf, len);
}
command result_t BlockWrite.erase[uint8_t id]() {
storage_addr_t physicalAddr;
if (admitRequest(S_ERASE, id) == FAIL)
return FAIL;
physicalAddr = call ActualFV.physicalAddr[client](0);
if (!call HALAT45DB.erase(physicalAddr >> AT45_PAGE_SIZE_LOG2, AT45_ERASE))
post signalFail();
return SUCCESS;
}
command result_t BlockWrite.commit[uint8_t id]() {
if (admitRequest(S_COMMIT, id) == FAIL)
return FAIL;
if (!call HALAT45DB.syncAll())
post signalFail();
return SUCCESS;
}
command result_t BlockRead.read[uint8_t id](block_addr_t addr, uint8_t* buf, block_addr_t len) {
return newRequest(S_READ, addr, buf, len);
}
command result_t BlockRead.verify[uint8_t id]() {
return FAIL;
}
command result_t BlockRead.computeCrc[uint8_t id](block_addr_t addr, block_addr_t len) {
if (state == S_IDLE)
crc = 0;
return newRequest(S_CRC, addr, NULL, len);
}
result_t multipageDone(result_t result) {
if (bytesRemaining == 0 || result == FAIL)
signalDone(result);
else
continueRequest();
}
event result_t HALAT45DB.writeDone(result_t result) {
return multipageDone(result);
}
event result_t HALAT45DB.readDone(result_t result) {
return multipageDone(result);
}
event result_t HALAT45DB.computeCrcDone(result_t result, uint16_t newCrc) {
crc = newCrc;
return multipageDone(result);
}
event result_t HALAT45DB.eraseDone(result_t result) {
signalDone(result);
return SUCCESS;
}
event result_t HALAT45DB.syncDone(result_t result) {
signalDone(result);
return SUCCESS;
}
event result_t HALAT45DB.flushDone(result_t result) {
return SUCCESS;
}
default event result_t BlockWrite.writeDone[uint8_t id](result_t result) { return SUCCESS; }
default event result_t BlockWrite.eraseDone[uint8_t id](result_t result) { return SUCCESS; }
default event result_t BlockWrite.commitDone[uint8_t id](result_t result) { return SUCCESS; }
default event result_t BlockRead.readDone[uint8_t id](result_t result) { return SUCCESS; }
default event result_t BlockRead.verifyDone[uint8_t id](result_t result) { return SUCCESS; }
default event result_t BlockRead.computeCrcDone[uint8_t id](result_t result, uint16_t crcResult) { return SUCCESS; }
}
--- NEW FILE: BlockWrite.nc ---
// $Id: BlockWrite.nc,v 1.1 2005/01/22 00:26:30 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
*/
includes BlockStorage;
interface BlockWrite {
command result_t write(block_addr_t addr, uint8_t* buf, block_addr_t len);
event result_t writeDone(result_t result);
command result_t erase();
event result_t eraseDone(result_t result);
command result_t commit();
event result_t commitDone(result_t result);
}
--- NEW FILE: FlashVolume.h ---
// $Id: FlashVolume.h,v 1.1 2005/01/22 00:26:31 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
*/
#ifndef __FLASH_VOLUME_H__
#define __FLASH_VOLUME_H__
typedef uint32_t storage_addr_t;
#define FV_INVALID_VOLUME 0xff
#define FV_VOLUME_SIZE ((storage_addr_t)0x10000L)
#define FV_FACTORY_IMAGE 7
#define FV_MAX_VOLUMES 8
#define FV_INVALID_ADDR ((storage_addr_t)-1)
#endif
--- NEW FILE: FlashVolume.nc ---
// $Id: FlashVolume.nc,v 1.1 2005/01/22 00:26:31 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
*/
includes FlashVolume;
interface FlashVolume {
command result_t mount(uint8_t uid);
command storage_addr_t physicalAddr(storage_addr_t volumeAddr);
command uint8_t physicalAddrToVolume(storage_addr_t addr);
}
--- NEW FILE: FlashVolumeC.nc ---
// $Id: FlashVolumeC.nc,v 1.1 2005/01/22 00:26:31 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
*/
configuration FlashVolumeC {
provides {
interface FlashVolume[uint8_t id];
interface StdControl;
}
}
implementation {
components
FlashVolumeM;
FlashVolume = FlashVolumeM;
StdControl = FlashVolumeM;
}
--- NEW FILE: FlashVolumeM.nc ---
// $Id: FlashVolumeM.nc,v 1.1 2005/01/22 00:26:31 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2004 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/*
* @author: Jonathan Hui <jwhui at cs.berkeley.edu>
*/
module FlashVolumeM {
provides {
interface FlashVolume[uint8_t id];
interface StdControl;
}
}
implementation {
enum {
NUM_VOLUMES = uniqueCount("FlashVolume"),
};
uint8_t volumeMap[NUM_VOLUMES];
command result_t StdControl.init() {
uint8_t i;
for ( i = 0; i < NUM_VOLUMES; i++ )
volumeMap[i] = FV_INVALID_VOLUME;
return SUCCESS;
}
command result_t StdControl.start() { return SUCCESS; }
command result_t StdControl.stop() { return SUCCESS; }
command result_t FlashVolume.mount[uint8_t id](uint8_t uid) {
if (uid >= FV_MAX_VOLUMES)
return FAIL;
volumeMap[id] = uid;
return SUCCESS;
}
command storage_addr_t FlashVolume.physicalAddr[uint8_t id](storage_addr_t volumeAddr) {
storage_addr_t base = (storage_addr_t)volumeMap[id]*FV_VOLUME_SIZE;
if (volumeMap[id] == FV_INVALID_VOLUME
|| volumeAddr >= FV_VOLUME_SIZE)
return FV_INVALID_ADDR;
return base + volumeAddr;
}
command uint8_t FlashVolume.physicalAddrToVolume[uint8_t id](storage_addr_t addr) {
return addr / FV_VOLUME_SIZE;
}
}
--- NEW FILE: HALAT45DB.h ---
// $Id: HALAT45DB.h,v 1.1 2005/01/22 00:26:31 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2003 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*
* Copyright (c) 2002-2003 Intel Corporation
* All rights reserved.
*
* This file is distributed under the terms in the attached INTEL-LICENSE
* file. If you do not find these files, copies can be found by writing to
* Intel Research Berkeley, 2150 Shattuck Avenue, Suite 1300, Berkeley, CA,
* 94704. Attention: Intel License Inquiry.
*/
#ifndef HALAT45DB_H
#define HALAT45DB_H
// flash characteristics
enum {
AT45_MAX_PAGES = 2048,
AT45_PAGE_SIZE = 264,
AT45_PAGE_SIZE_LOG2 = 8 // For those who want to ignore the last 8 bytes
};
enum {
AT45_ERASE,
AT45_DONT_ERASE,
AT45_PREVIOUSLY_ERASED
};
typedef uint16_t at45page_t;
typedef uint16_t at45pageoffset_t; /* 0 to AT45_PAGE_SIZE - 1 */
#endif
--- NEW FILE: HALAT45DB.nc ---
// $Id: HALAT45DB.nc,v 1.1 2005/01/22 00:26:31 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2003 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*
* Copyright (c) 2002-2003 Intel Corporation
* All rights reserved.
*
* This file is distributed under the terms in the attached INTEL-LICENSE
* file. If you do not find these files, copies can be found by writing to
* Intel Research Berkeley, 2150 Shattuck Avenue, Suite 1300, Berkeley, CA,
* 94704. Attention: Intel License Inquiry.
*/
includes AT45DB.h;
interface HALAT45DB {
command result_t write(at45page_t page, at45pageoffset_t offset,
void *data, at45pageoffset_t n);
event result_t writeDone(result_t result);
command result_t erase(at45page_t page, uint8_t eraseKind);
event result_t eraseDone(result_t result);
command result_t sync(at45page_t page);
command result_t syncAll();
event result_t syncDone(result_t result);
command result_t flush(at45page_t page);
command result_t flushAll();
event result_t flushDone(result_t result);
command result_t read(at45page_t page, at45pageoffset_t offset,
void *data, at45pageoffset_t n);
event result_t readDone(result_t result);
command result_t computeCrc(at45page_t page, at45pageoffset_t offset,
at45pageoffset_t n);
event result_t computeCrcDone(result_t result, uint16_t crc);
}
--- NEW FILE: HALAT45DBC.nc ---
// $Id: HALAT45DBC.nc,v 1.1 2005/01/22 00:26:31 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2003 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*
* Copyright (c) 2002-2003 Intel Corporation
* All rights reserved.
*
* This file is distributed under the terms in the attached INTEL-LICENSE
* file. If you do not find these files, copies can be found by writing to
* Intel Research Berkeley, 2150 Shattuck Avenue, Suite 1300, Berkeley, CA,
* 94704. Attention: Intel License Inquiry.
*/
/*
*
* Authors: Jason Hill, David Gay, Philip Levis
* Date last modified: 6/25/02
*
*/
/**
* @author Jason Hill
* @author David Gay
* @author Philip Levis
*/
configuration PageEEPROMC
{
provides {
interface StdControl;
interface PageEEPROM[uint8_t client];
}
}
implementation
{
components PageEEPROMM, PageEEPROMShare, HPLFlash, NoLeds as Leds;
StdControl = PageEEPROMM;
PageEEPROM = PageEEPROMShare;
PageEEPROMShare.ActualEEPROM -> PageEEPROMM;
PageEEPROMM.FlashSPI -> HPLFlash;
PageEEPROMM.FlashControl -> HPLFlash;
PageEEPROMM.FlashIdle -> HPLFlash;
PageEEPROMM.getCompareStatus -> HPLFlash;
PageEEPROMM.FlashSelect -> HPLFlash;
PageEEPROMM.Leds -> Leds;
}
--- NEW FILE: HALAT45DBM.nc ---
// $Id: HALAT45DBM.nc,v 1.1 2005/01/22 00:26:31 idgay Exp $
/* tab:4
* "Copyright (c) 2000-2003 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*
* Copyright (c) 2002-2003 Intel Corporation
* All rights reserved.
*
* This file is distributed under the terms in the attached INTEL-LICENSE
* file. If you do not find these files, copies can be found by writing to
* Intel Research Berkeley, 2150 Shattuck Avenue, Suite 1300, Berkeley, CA,
* 94704. Attention: Intel License Inquiry.
*/
includes crc;
includes HALAT45DB;
module HALAT45DBM {
provides {
interface StdControl;
interface PageEEPROM as HALAT45DB;
}
uses {
interface HPLAT45DB;
}
}
implementation
{
#define CHECKARGS
#if 0
uint8_t work[20];
uint8_t woffset;
void wdbg(uint8_t x) {
work[woffset++] = x;
if (woffset == sizeof work)
woffset = 0;
}
#else
#define wdbg(n)
#endif
enum { // requests
IDLE,
R_READ,
R_READCRC,
R_WRITE,
R_ERASE,
R_SYNC,
R_SYNCALL,
R_FLUSH,
R_FLUSHALL
};
uint8_t request;
uint8_t *reqBuf;
at45pageoffset_t reqOffset, reqBytes;
at45page_t reqPage;
bool broken; // Write failed. Fail all subsequent requests.
enum {
P_READ,
P_READCRC,
P_WRITE,
P_FLUSH,
P_FILL,
P_ERASE,
P_COMPARE,
P_COMPARE_CHECK
};
struct {
at45page_t page;
bool busy : 1;
bool clean : 1;
bool erased : 1;
uint8_t unchecked : 2;
} buffer[2];
uint8_t selected; // buffer used by the current op
uint8_t checking;
bool flashBusy;
// Select a command for the current buffer
#define OPN(n, name) ((n) ? name ## 1 : name ## 2)
#define OP(name) OPN(selected, name)
command result_t StdControl.init() {
request = IDLE;
flashBusy = TRUE;
// pretend we're on an invalid non-existent page
buffer[0].page = buffer[1].page = AT45_MAX_PAGES;
buffer[0].busy = buffer[1].busy = FALSE;
buffer[0].clean = buffer[1].clean = TRUE;
buffer[0].unchecked = buffer[1].unchecked = 0;
buffer[0].erased = buffer[1].erased = FALSE;
return SUCCESS;
}
command result_t StdControl.start() {
return SUCCESS;
}
command result_t StdControl.stop() {
return SUCCESS;
}
void flashIdle() {
flashBusy = buffer[0].busy = buffer[1].busy = FALSE;
}
void requestDone(result_t result, uint16_t computedCrc);
void handleRWRequest();
task void taskSuccess() {
requestDone(SUCCESS, 0);
}
task void taskFail() {
requestDone(FAIL, 0);
}
void checkBuffer(uint8_t buf) {
call HPLAT45DB.compare(OPN(buf, AT45_C_COMPARE_BUFFER), buffer[buf].page);
checking = buf;
}
void flushBuffer() {
call HPLAT45DB.flush(buffer[selected].erased ?
OP(AT45_C_QFLUSH_BUFFER) :
OP(AT45_C_FLUSH_BUFFER),
buffer[selected].page);
}
event result_t HPLAT45DB.waitIdleDone() {
flashIdle();
// Eager compare - this steals the current command
#if 0
if ((buffer[0].unchecked || buffer[1].unchecked) &&
cmdPhase != P_COMPARE)
checkBuffer(buffer[0].unchecked ? 0 : 1);
else
#endif
handleRWRequest();
return SUCCESS;
}
event result_t HPLAT45DB.waitCompareDone(bool ok) {
flashIdle();
if (ok)
buffer[checking].unchecked = 0;
else if (buffer[checking].unchecked < 2)
buffer[checking].clean = FALSE;
else
{
broken = TRUE; // write failed. refuse all further reqs
requestDone(FAIL, 0);
return SUCCESS;
}
handleRWRequest();
return SUCCESS;
}
event result_t HPLAT45DB.readDone() {
requestDone(SUCCESS, 0);
return SUCCESS;
}
event result_t HPLAT45DB.writeDone() {
buffer[selected].clean = FALSE;
buffer[selected].unchecked = 0;
requestDone(SUCCESS, 0);
return SUCCESS;
}
event result_t HPLAT45DB.crcDone(uint16_t crc) {
requestDone(SUCCESS, crc);
return SUCCESS;
}
event result_t HPLAT45DB.flushDone() {
flashBusy = TRUE;
buffer[selected].clean = buffer[selected].busy = TRUE;
buffer[selected].unchecked++;
buffer[selected].erased = FALSE;
handleRWRequest();
return SUCCESS;
}
event result_t HPLAT45DB.compareDone() {
flashBusy = TRUE;
buffer[checking].busy = TRUE;
// The 10us wait makes old mica motes (Atmega 103) happy, for
// some mysterious reason (w/o this wait, the first compare
// always fail, even though the compare after the rewrite
// succeeds...)
TOSH_uwait(10);
call HPLAT45DB.waitCompare();
return SUCCESS;
}
event result_t HPLAT45DB.fillDone() {
flashBusy = TRUE;
buffer[selected].page = reqPage;
buffer[selected].clean = buffer[selected].busy = TRUE;
buffer[selected].erased = FALSE;
handleRWRequest();
return SUCCESS;
}
event result_t HPLAT45DB.eraseDone() {
flashBusy = TRUE;
// The buffer contains garbage, but we don't care about the state
// of bits on this page anyway (if we do, we'll perform a
// subsequent write)
buffer[selected].page = reqPage;
buffer[selected].clean = TRUE;
buffer[selected].erased = TRUE;
requestDone(SUCCESS, 0);
return SUCCESS;
}
result_t syncOrFlushAll(uint8_t newReq);
void handleRWRequest() {
if (reqPage == buffer[selected].page)
switch (request)
{
case R_ERASE:
switch (reqOffset)
{
case AT45_ERASE:
if (flashBusy)
call HPLAT45DB.waitIdle();
else
call HPLAT45DB.erase(AT45_C_ERASE_PAGE, reqPage);
break;
case AT45_PREVIOUSLY_ERASED:
// We believe the user...
buffer[selected].erased = TRUE;
/* Fallthrough */
case AT45_DONT_ERASE:
// The buffer contains garbage, but we don't care about the state
// of bits on this page anyway (if we do, we'll perform a
// subsequent write)
buffer[selected].clean = TRUE;
requestDone(SUCCESS, 0);
break;
}
break;
case R_SYNC: case R_SYNCALL:
if (buffer[selected].clean && buffer[selected].unchecked)
{
checkBuffer(selected);
return;
}
/* fall through */
case R_FLUSH: case R_FLUSHALL:
if (!buffer[selected].clean)
flushBuffer();
else if (request == R_FLUSH || request == R_SYNC)
post taskSuccess();
else
{
// Check for more dirty pages
uint8_t oreq = request;
request = IDLE;
syncOrFlushAll(oreq);
}
break;
case R_READ:
if (buffer[selected].busy)
call HPLAT45DB.waitIdle();
else
call HPLAT45DB.read(OP(AT45_C_READ_BUFFER), 0, reqOffset,
reqBuf, reqBytes);
break;
case R_READCRC:
if (buffer[selected].busy)
call HPLAT45DB.waitIdle();
else
call HPLAT45DB.crc(OP(AT45_C_READ_BUFFER), 0, reqOffset, reqBytes);
break;
case R_WRITE:
if (buffer[selected].busy)
call HPLAT45DB.waitIdle();
else
call HPLAT45DB.write(OP(AT45_C_WRITE_BUFFER), 0, reqOffset,
reqBuf, reqBytes);
break;
}
else if (!buffer[selected].clean)
flushBuffer();
else if (buffer[selected].unchecked)
checkBuffer(selected);
else
{
// just get the new page (except for erase)
if (request == R_ERASE)
{
buffer[selected].page = reqPage;
handleRWRequest();
}
else if (flashBusy)
call HPLAT45DB.waitIdle();
else
call HPLAT45DB.fill(OP(AT45_C_FILL_BUFFER), reqPage);
}
}
void requestDone(result_t result, uint16_t computedCrc) {
uint8_t orequest = request;
request = IDLE;
switch (orequest)
{
case R_READ: signal HALAT45DB.readDone(result); break;
case R_READCRC: signal HALAT45DB.computeCrcDone(result, computedCrc); break;
case R_WRITE: signal HALAT45DB.writeDone(result); break;
case R_SYNC: case R_SYNCALL: signal HALAT45DB.syncDone(result); break;
case R_FLUSH: case R_FLUSHALL: signal HALAT45DB.flushDone(result); break;
case R_ERASE: signal HALAT45DB.eraseDone(result); break;
}
}
result_t newRequest(uint8_t req, at45page_t page,
at45pageoffset_t offset,
void *reqdata, at45pageoffset_t n) {
#ifdef CHECKARGS
if (page >= AT45_MAX_PAGES || offset >= AT45_PAGE_SIZE ||
n > AT45_PAGE_SIZE || offset + n > AT45_PAGE_SIZE)
return FAIL;
#endif
if (request != IDLE)
return FAIL;
request = req;
if (broken)
{
post taskFail();
return SUCCESS;
}
reqBuf = reqdata;
reqBytes = n;
reqPage = page;
reqOffset = offset;
if (page == buffer[0].page)
selected = 0;
else if (page == buffer[1].page)
selected = 1;
else
selected = !selected; // LRU with 2 buffers...
handleRWRequest();
return SUCCESS;
}
command result_t HALAT45DB.read(at45page_t page, at45pageoffset_t offset,
void *reqdata, at45pageoffset_t n) {
return newRequest(R_READ, page, offset, reqdata, n);
}
command result_t HALAT45DB.computeCrc(at45page_t page,
at45pageoffset_t offset,
at45pageoffset_t n) {
if (n == 0)
{
request = R_READCRC;
post taskSuccess();
return SUCCESS;
}
else
return newRequest(R_READCRC, page, offset, NULL, n);
}
command result_t HALAT45DB.write(at45page_t page, at45pageoffset_t offset,
void *reqdata, at45pageoffset_t n) {
return newRequest(R_WRITE, page, offset, reqdata, n);
}
command result_t HALAT45DB.erase(at45page_t page, uint8_t eraseKind) {
return newRequest(R_ERASE, page, eraseKind, NULL, 0);
}
result_t syncOrFlush(at45page_t page, uint8_t newReq) {
if (request != IDLE)
return FAIL;
request = newReq;
if (broken)
{
post taskFail();
return SUCCESS;
}
else if (buffer[0].page == page)
selected = 0;
else if (buffer[1].page == page)
selected = 1;
else
{
post taskSuccess();
return SUCCESS;
}
buffer[selected].unchecked = 0;
handleRWRequest();
return SUCCESS;
}
command result_t HALAT45DB.sync(at45page_t page) {
return syncOrFlush(page, R_SYNC);
}
command result_t HALAT45DB.flush(at45page_t page) {
return syncOrFlush(page, R_FLUSH);
}
result_t syncOrFlushAll(uint8_t newReq) {
if (request != IDLE)
return FAIL;
request = newReq;
if (broken)
{
post taskFail();
return SUCCESS;
}
else if (!buffer[0].clean)
selected = 0;
else if (!buffer[1].clean)
selected = 1;
else
{
post taskSuccess();
return SUCCESS;
}
buffer[selected].unchecked = 0;
handleRWRequest();
return SUCCESS;
}
command result_t HALAT45DB.syncAll() {
return syncOrFlushAll(R_SYNCALL);
}
command result_t HALAT45DB.flushAll() {
return syncOrFlushAll(R_FLUSHALL);
}
}
--- NEW FILE: HPLAT45DB.h ---
enum { // commands we're executing (all SPI Mode 0 or 3)
AT45_C_READ_BUFFER1 = 0xd4,
AT45_C_READ_BUFFER2 = 0xd6,
AT45_C_WRITE_BUFFER1 = 0x84,
AT45_C_WRITE_BUFFER2 = 0x87,
AT45_C_FILL_BUFFER1 = 0x53,
AT45_C_FILL_BUFFER2 = 0x55,
AT45_C_FLUSH_BUFFER1 = 0x83,
AT45_C_FLUSH_BUFFER2 = 0x86,
AT45_C_QFLUSH_BUFFER1 = 0x88,
AT45_C_QFLUSH_BUFFER2 = 0x89,
AT45_C_COMPARE_BUFFER1 = 0x60,
AT45_C_COMPARE_BUFFER2 = 0x61,
AT45_C_REQ_STATUS = 0xd7,
AT45_C_ERASE_PAGE = 0x81
};
--- NEW FILE: HPLAT45DB.nc ---
includes HPLAT45DB;
interface HPLAT45DB {
command result_t waitIdle();
event result_t waitIdleDone();
command result_t waitCompare();
event result_t waitCompareDone(bool compareOk);
command result_t fill(uint8_t cmd, at45page_t page);
event result_t fillDone();
command result_t flush(uint8_t cmd, at45page_t page);
event result_t flushDone();
command result_t compare(uint8_t cmd, at45page_t page);
event result_t compareDone();
command result_t erase(uint8_t cmd, at45page_t page);
event result_t eraseDone();
command result_t read(uint8_t cmd, at45page_t page, at45pageoffset_t offset,
uint8_t *data, at45pageoffset_t count);
event result_t readDone();
command result_t crc(uint8_t cmd, at45page_t page, at45pageoffset_t offset,
at45pageoffset_t count);
event result_t crcDone(uint16_t computedCrc);
command result_t write(uint8_t cmd, at45page_t page, at45pageoffset_t offset,
uint8_t *data, at45pageoffset_t count);
event result_t writeDone();
}
--- NEW FILE: HPLAT45DBByte.nc ---
module HPLAT45DBByte {
provides interface HPLAT45DB;
uses {
interface SlavePin as FlashSelect;
interface FastSPI as FlashSPI;
interface Resource as FlashIdle;
command bool getCompareStatus();
}
}
implementation
{
enum {
P_IDLE,
P_SEND_CMD,
P_READ,
P_READ_CRC,
P_WRITE,
P_WAIT_IDLE,
P_WAIT_COMPARE,
P_WAIT_COMPARE_OK,
P_FILL,
P_FLUSH,
P_COMPARE,
P_ERASE
};
uint8_t status = P_IDLE;
uint16_t computedCrc;
event result_t FlashSelect.notifyHigh() {
uint8_t s = status;
status = P_IDLE;
switch (s)
{
case P_IDLE: break;
case P_WAIT_IDLE:
signal HPLAT45DB.waitIdleDone();
break;
case P_WAIT_COMPARE:
signal HPLAT45DB.waitCompareDone(FALSE);
break;
case P_WAIT_COMPARE_OK:
signal HPLAT45DB.waitCompareDone(TRUE);
break;
case P_READ_CRC:
signal HPLAT45DB.crcDone(computedCrc);
break;
case P_FILL:
signal HPLAT45DB.fillDone();
break;
case P_FLUSH:
signal HPLAT45DB.flushDone();
break;
case P_COMPARE:
signal HPLAT45DB.compareDone();
break;
case P_ERASE:
signal HPLAT45DB.eraseDone();
break;
case P_READ:
signal HPLAT45DB.readDone();
break;
case P_WRITE:
signal HPLAT45DB.writeDone();
break;
}
return SUCCESS;
}
event result_t FlashIdle.available() {
if (status == P_WAIT_COMPARE && call getCompareStatus())
status = P_WAIT_COMPARE_OK;
call FlashSelect.high(TRUE);
return SUCCESS;
}
void requestFlashStatus() {
call FlashSelect.low();
call FlashSPI.txByte(AT45_C_REQ_STATUS);
if (call FlashIdle.wait() == FAIL) // already done
signal FlashIdle.available();
}
command result_t HPLAT45DB.waitIdle() {
status = P_WAIT_IDLE;
requestFlashStatus();
return SUCCESS;
}
command result_t HPLAT45DB.waitCompare() {
status = P_WAIT_COMPARE;
requestFlashStatus();
return SUCCESS;
}
void execCommand(uint8_t op, uint8_t reqCmd, uint8_t dontCare,
at45page_t page, at45pageoffset_t offset,
uint8_t *data, at45pageoffset_t dataCount) {
uint8_t cmd[4];
uint8_t in = 0, out = 0;
uint8_t *ptr;
at45pageoffset_t count;
uint16_t crc = 0;
uint8_t lphase = P_SEND_CMD;
status = op;
/* For a 3% speedup, we could use labels and goto *.
But: very gcc-specific. Also, need to do
asm ("ijmp" : : "z" (state))
instead of goto *state
*/
// page (2 bytes) and highest bit of offset
cmd[0] = reqCmd;
cmd[1] = page >> 7;
cmd[2] = page << 1 | offset >> 8;
cmd[3] = offset; // low-order 8 bits
ptr = cmd;
count = 4 + dontCare;
call FlashSelect.low();
for (;;)
{
if (lphase == P_READ_CRC)
{
crc = crcByte(crc, in);
--count;
if (!count)
{
computedCrc = crc;
break;
}
}
else if (lphase == P_SEND_CMD)
{
out = *ptr++;
count--;
if (!count)
{
lphase = op;
ptr = data;
count = dataCount;
}
}
else if (lphase == P_READ)
{
*ptr++ = in;
--count;
if (!count)
break;
}
else if (lphase == P_WRITE)
{
if (!count)
break;
out = *ptr++;
--count;
}
else /* P_COMMAND */
break;
in = call FlashSPI.txByte(out);
}
call FlashSelect.high(TRUE);
}
command result_t HPLAT45DB.fill(uint8_t cmd, at45page_t page) {
execCommand(P_FILL, cmd, 0, page, 0, NULL, 0);
return SUCCESS;
}
command result_t HPLAT45DB.flush(uint8_t cmd, at45page_t page) {
execCommand(P_FLUSH, cmd, 0, page, 0, NULL, 0);
return SUCCESS;
}
command result_t HPLAT45DB.compare(uint8_t cmd, at45page_t page) {
execCommand(P_COMPARE, cmd, 0, page, 0, NULL, 0);
return SUCCESS;
}
command result_t HPLAT45DB.erase(uint8_t cmd, at45page_t page) {
execCommand(P_ERASE, cmd, 0, page, 0, NULL, 0);
return SUCCESS;
}
command result_t HPLAT45DB.read(uint8_t cmd,
at45page_t page, at45pageoffset_t offset,
uint8_t *data, at45pageoffset_t count) {
execCommand(P_READ, cmd, 2, page, offset, data, count);
return SUCCESS;
}
command result_t HPLAT45DB.crc(uint8_t cmd,
at45page_t page, at45pageoffset_t offset,
at45pageoffset_t count) {
execCommand(P_READ_CRC, cmd, 2, page, offset, NULL, count);
return SUCCESS;
}
command result_t HPLAT45DB.write(uint8_t cmd,
at45page_t page, at45pageoffset_t offset,
uint8_t *data, at45pageoffset_t count) {
execCommand(P_WRITE, cmd, 0, page, offset, data, count);
return SUCCESS;
}
}
--- NEW FILE: PageEEPROMC.nc ---
configuration PageEEPROMC
{
provides {
interface StdControl;
interface PageEEPROM[uint8_t client];
}
}
implementation
{
components HALAT45DBM, PageEEPROMShare, HPLAT45DBC;
StdControl = HALAT45DBM;
StdControl = HPLAT45DBC;
PageEEPROM = PageEEPROMShare;
PageEEPROMShare.ActualEEPROM -> HALAT45DBM;
HALAT45DBM.HPLAT45DB -> HPLAT45DBC;
}
More information about the Tinyos-beta-commits
mailing list