# SFBSDRaw.h

Go to the documentation of this file.

    00001 /*                                             -*- mode:C++; fill-column:100 -*-
    00002   SFBSDRaw.h - Bit-banged SDCard raw disk access.
    00003   Copyright (C) 2010 The Regents of the University of New Mexico
    00004
    00005   This library is free software; you can redistribute it and/or
    00006   modify it under the terms of the GNU Lesser General Public
    00007   License as published by the Free Software Foundation; either
    00008   version 2.1 of the License, or (at your option) any later version.
    00009
    00010   This library is distributed in the hope that it will be useful,
    00011   but WITHOUT ANY WARRANTY; without even the implied warranty of
    00012   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    00013   Lesser General Public License for more details.
    00014
    00015   You should have received a copy of the GNU General Public License
    00016   along with this library; if not, write to the Free Software
    00017   Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301
    00018   USA
    00019
    00020   $Id$
    00021  */
    00022
    00030 #ifndef SFBSDRAW_H
    00031 #define SFBSDRAW_H
    00032
    00033 #include "SFBTypes.h"           // For u32 etc
    00034 #include "SFBConstants.h"       // For FACE_COUNT
    00035
    00036 #define SDRAW_BLOCK_SIZE_BIT_COUNT 9
    00037 #define SDRAW_BLOCK_SIZE (1<<(SDRAW_BLOCK_SIZE_BIT_COUNT)) // 512 bytes per block
    00038 #define SDRAW_BLOCK_SIZE_BIT_MASK ((SDRAW_BLOCK_SIZE)-1)
    00039
    00044 struct SDRawDiskInfo {
    00045   u32 serialNumber;
    00046   u32 blockCount;
    00047   u8 manufacturer;
    00048   u8 oem[2+1];
    00049   u8 product[5+1];
    00050   u8 revision;
    00051   u8 year;
    00052   u8 month;
    00053   u8 format;
    00054   bool copy;
    00055   bool writeProtect;
    00056   bool writeProtectTemporary;
    00057 };
    00058
    00113 class SDRaw {
    00114 public:
    00118   enum State {
    00119     NOT_BEGUN=0,
    00120     UNINITTED,
    00121     RESET_FAILED,
    00122     CRC_ON_FAILED,
    00123     TYPE_CHECK_FAILED,
    00124     OP_COND_FAILED,
    00125     READ_OCR_FAILED,
    00126     CONFIG_FAILED,
    00127     ACTIVE,
    00128     INACTIVE_READ,
    00129     INACTIVE_WRITE,
    00130     ERROR_READ_SINGLE_BLOCK,
    00131     ERROR_READ_REGISTER,
    00132     ERROR_READ_TIMEOUT_DATA,
    00133     ERROR_READ_CRC_DATA,
    00134     ERROR_BAD_CSD_VERSION,
    00135     ERROR_WRITE_TIMEOUT_DATA,
    00136     ERROR_WRITE_SINGLE_BLOCK
    00137   };
    00138
    00147   void begin(u8 face) ;
    00148
    00165   void begin(u8 face, u8 CSPin, u8 clkPin, u8 MOSIpin, u8 MISOpin) ;
    00166
    00173   bool end() ;
    00174
    00178   u32 getState() { return status; }
    00179
    00185   u32 getBlockCount() { return isActive() ? blockCapacity : 0; }
    00186
    00191   u64 getByteCount() { return ((u64) getBlockCount())<<SDRAW_BLOCK_SIZE_BIT_COUNT; }
    00192
    00197   u8 getFace() { return sdFace; }
    00198
    00210   bool init() ;
    00211
    00214   bool isActive() { return getState()==ACTIVE; }
    00215
    00223   bool getInfo(SDRawDiskInfo & info) ;
    00224
    00248   bool setBlockBuffer(u8 * buffer, u32 bufferLength) ;
    00249
    00281   bool read(u64 address, u8* data, u32 length) ;
    00282
    00312   bool readBlock(u32 blockNumber, u8* buffer, u32 blockOffset = 0, u32 length = 512) ;
    00313
    00342   bool write(u64 address, const u8* data, u32 length) ;
    00343
    00359   bool writeBlock(u32 blockNumber, const u8* buffer) ;
    00360
    00369   bool sync() ;
    00370
    00376   bool isSDHC() { return (flags&HC_CARD); }
    00377
    00381   void setSpiLog(bool val) { if (val) flags |= SPI_LOG; else flags &= ~SPI_LOG; }
    00382
    00394   u32 readStatus() ;
    00395
    00396 private:
    00397   enum { SHORT_TRIES = 50, LONG_TRIES = 50000 };
    00398
    00399   enum {
    00400     BLOCK_DIRTY = 0x01,
    00401     HC_CARD     = 0x02,
    00402     SPI_LOG     = 0x04,
    00403     FLAG_RSRV3  = 0x08,
    00404     FLAG_RSRV4  = 0x10,
    00405     FLAG_RSRV5  = 0x20,
    00406     FLAG_RSRV6  = 0x40,
    00407     FLAG_RSRV7  = 0x80
    00408   };
    00409   u32 blockCapacity;            // Number of blocks that fit on the disk
    00410   u32 cachedBlockNumber;        // Number of currently buffered block
    00411   u8 * cachedBlock;             // Zero for no buffering or ptr to 512 bytes
    00412   u8 flags;                     // Dirty bit
    00413   u8 status;                    // Operational status
    00414   u8 sdFace;                    // Face to power cycle to init card
    00415   u8 sdCSel;                    // Pin for chip select
    00416   u8 sdClk;                     // Pin for clock
    00417   u8 sdMOSI;                    // Pin for master-out-slave-in
    00418   u8 sdMISO;                    // Pin for master-in-slave-out
    00419
    00420   void startTransaction() ;
    00421   void endTransaction() ;
    00422
    00423   bool dieWith(u32 newStatus) ;
    00424
    00425   bool readRegister(u32 cmd, u8 reg[16]);
    00426
    00427   void sendBitsSlow(u32 data, u32 bitCount) ;  // Used during init only
    00428   u32 recvBitsSlow(u32 bitCount) ;             // Used during init only
    00429
    00430   void sendBits(u32 bits, u32 bitCount) ;
    00431   u32 recvBits(u32 bitCount) ;
    00432
    00433   void sendByte(u8 data) { sendBits(data,8); }
    00434   u8 recvByte() { return (u8) recvBits(8); }
    00435
    00436   u8 sendCmd(u8 cmd, u32 arg) ;
    00437
    00438   bool loadCache(u32 blockNumber) ;
    00439   bool writeBuffered(u64 offset, const u8* buffer, u32 length) ;
    00440   bool readBuffered(u64 offset, u8* buffer, u32 length) ;
    00441
    00442 };
    00443
    00444 #endif /* SFBSDRAW_H */