STORAGE: Pull request 3762 review feedback changes.

- Fixing code formatting errors with astyle tool.
- Replaced use of TOOLCHAIN_xxx macros with compiler emitted macros.
- Added const to BlockDevice::get_xxx_size() member functions.
- Added documentation for FAT filesystem thread support.
- Added documentation for fat_filesystem_set_errno().
- Added documentation clarifying the reasons for errno/stat symbol definitions in retarget.h.
- Removed FAT filesystem from mbed 2 testing.
- Fixed FATMisc.h Copyright (c) 2016 year to 2017 as its a new file.
- Removed #ifndef NDEBUG from HeapBlockDevice.cpp.
- Removed unnecessary todo comment in retarget.cpp.
pull/3762/head
Simon Hughes 2017-02-22 15:19:02 +00:00
parent b8e31c8156
commit 840c77793b
22 changed files with 254 additions and 225 deletions

View File

@ -27,7 +27,7 @@ using namespace utest::v1;
* stack tracking statistics are enabled. If this is the case, build dummy
* tests.
*/
#if ! defined(TOOLCHAIN_IAR) && ! defined(TARGET_KL25Z) && ! defined(MBED_STACK_STATS_ENABLED)
#if ! defined(__ICCARM__) && ! defined(TARGET_KL25Z) && ! defined(MBED_STACK_STATS_ENABLED)
#define BLOCK_SIZE 512
#define HEAP_BLOCK_DEVICE_TEST_01 test_read_write
@ -64,7 +64,7 @@ void test_read_write() {
TEST_ASSERT_EQUAL(0, err);
}
#else /* ! defined(TOOLCHAIN_IAR) && ! defined(TARGET_KL25Z) && ! defined(MBED_STACK_STATS_ENABLED) */
#else /* ! defined(__ICCARM__) && ! defined(TARGET_KL25Z) && ! defined(MBED_STACK_STATS_ENABLED) */
#define HEAP_BLOCK_DEVICE_TEST_01 heap_block_device_test_dummy
@ -78,7 +78,7 @@ static control_t heap_block_device_test_dummy()
return CaseNext;
}
#endif /* ! defined(TOOLCHAIN_IAR) && ! defined(TARGET_KL25Z) && ! defined(MBED_STACK_STATS_ENABLED) */
#endif /* ! defined(__ICCARM__) && ! defined(TARGET_KL25Z) && ! defined(MBED_STACK_STATS_ENABLED) */
// Test setup
utest::v1::status_t test_setup(const size_t number_of_cases) {

View File

@ -32,7 +32,7 @@ bd_error_t BlockDevice::write(const void *buffer, bd_addr_t addr, bd_size_t size
return program(buffer, addr, size);
}
bd_size_t BlockDevice::get_write_size()
bd_size_t BlockDevice::get_write_size() const
{
return get_erase_size();
}
@ -52,24 +52,24 @@ static bool is_aligned(uint64_t x, uint64_t alignment)
bool BlockDevice::is_valid_read(bd_addr_t addr, bd_size_t size)
{
return (
is_aligned(addr, get_read_size()) &&
is_aligned(size, get_read_size()) &&
addr + size <= this->size());
is_aligned(addr, get_read_size()) &&
is_aligned(size, get_read_size()) &&
addr + size <= this->size());
}
bool BlockDevice::is_valid_erase(bd_addr_t addr, bd_size_t size)
{
return (
is_aligned(addr, get_erase_size()) &&
is_aligned(size, get_erase_size()) &&
addr + size <= this->size());
is_aligned(addr, get_erase_size()) &&
is_aligned(size, get_erase_size()) &&
addr + size <= this->size());
}
bool BlockDevice::is_valid_program(bd_addr_t addr, bd_size_t size)
{
return (
is_aligned(addr, get_program_size()) &&
is_aligned(size, get_program_size()) &&
addr + size <= this->size());
is_aligned(addr, get_program_size()) &&
is_aligned(size, get_program_size()) &&
addr + size <= this->size());
}

View File

@ -50,7 +50,8 @@ typedef uint64_t bd_size_t;
/** A hardware device capable of writing and reading blocks
*/
class BlockDevice {
class BlockDevice
{
public:
/** Lifetime of a block device
*/
@ -119,7 +120,7 @@ public:
*
* @return Size of a readable block in bytes
*/
virtual bd_size_t get_read_size() = 0;
virtual bd_size_t get_read_size() const = 0;
/** Get the size of a writeable block
*
@ -127,21 +128,21 @@ public:
* @note Must be a multiple of the read size, this is
* equivalent to the erase size of the device
*/
virtual bd_size_t get_write_size();
virtual bd_size_t get_write_size() const;
/** Get the size of a programable block
*
* @return Size of a programable block in bytes
* @note Must be a multiple of the read size
*/
virtual bd_size_t get_program_size() = 0;
virtual bd_size_t get_program_size() const = 0;
/** Get the size of a eraseable block
*
* @return Size of a eraseable block in bytes
* @note Must be a multiple of the program size
*/
virtual bd_size_t get_erase_size() = 0;
virtual bd_size_t get_erase_size() const = 0;
/** Get the total size of the underlying device
*

View File

@ -35,7 +35,7 @@ bd_error_t ChainingBlockDevice::init()
_erase_size = 0;
_size = 0;
// Initialize children block devices, find all sizes and
// Initialize children block devices, find all sizes and
// assert that block sizes are similar. We can't do this in
// the constructor since some block devices may need to be
// initialized before they know their block size/count
@ -183,17 +183,17 @@ bd_error_t ChainingBlockDevice::erase(bd_addr_t addr, bd_size_t size)
return 0;
}
bd_size_t ChainingBlockDevice::get_read_size()
bd_size_t ChainingBlockDevice::get_read_size() const
{
return _read_size;
}
bd_size_t ChainingBlockDevice::get_program_size()
bd_size_t ChainingBlockDevice::get_program_size() const
{
return _program_size;
}
bd_size_t ChainingBlockDevice::get_erase_size()
bd_size_t ChainingBlockDevice::get_erase_size() const
{
return _erase_size;
}

View File

@ -44,7 +44,8 @@
* BlockDevice *bds[] = {&mem1, &mem2};
* ChainingBlockDevice chainmem(bds);
*/
class ChainingBlockDevice : public BlockDevice {
class ChainingBlockDevice : public BlockDevice
{
public:
/** Lifetime of the memory block device
*
@ -62,7 +63,8 @@ public:
template <size_t Size>
ChainingBlockDevice(BlockDevice *(&bds)[Size])
: _bds(bds), _bd_count(sizeof(bds) / sizeof(bds[0]))
, _read_size(0), _program_size(0), _erase_size(0), _size(0) {
, _read_size(0), _program_size(0), _erase_size(0), _size(0)
{
}
/** Lifetime of the memory block device
@ -118,21 +120,21 @@ public:
*
* @return Size of a readable block in bytes
*/
virtual bd_size_t get_read_size();
virtual bd_size_t get_read_size() const;
/** Get the size of a programable block
*
* @return Size of a programable block in bytes
* @note Must be a multiple of the read size
*/
virtual bd_size_t get_program_size();
virtual bd_size_t get_program_size() const;
/** Get the size of a eraseable block
*
* @return Size of a eraseable block in bytes
* @note Must be a multiple of the program size
*/
virtual bd_size_t get_erase_size();
virtual bd_size_t get_erase_size() const;
/** Get the total size of the underlying device
*

View File

@ -24,8 +24,7 @@ HeapBlockDevice::HeapBlockDevice(bd_size_t size, bd_size_t block)
MBED_ASSERT(_count * _erase_size == size);
}
HeapBlockDevice::HeapBlockDevice(bd_size_t size,
bd_size_t read, bd_size_t program, bd_size_t erase)
HeapBlockDevice::HeapBlockDevice(bd_size_t size, bd_size_t read, bd_size_t program, bd_size_t erase)
: _read_size(read), _program_size(program), _erase_size(erase)
, _count(size / erase), _blocks(0)
{
@ -63,17 +62,17 @@ bd_error_t HeapBlockDevice::deinit()
return BD_ERROR_OK;
}
bd_size_t HeapBlockDevice::get_read_size()
bd_size_t HeapBlockDevice::get_read_size() const
{
return _read_size;
}
bd_size_t HeapBlockDevice::get_program_size()
bd_size_t HeapBlockDevice::get_program_size() const
{
return _program_size;
}
bd_size_t HeapBlockDevice::get_erase_size()
bd_size_t HeapBlockDevice::get_erase_size() const
{
return _erase_size;
}
@ -142,7 +141,6 @@ bd_error_t HeapBlockDevice::erase(bd_addr_t addr, bd_size_t size)
return BD_ERROR_PARAMETER;
}
#ifndef NDEBUG
while (size > 0) {
bd_addr_t hi = addr / _erase_size;
@ -153,7 +151,6 @@ bd_error_t HeapBlockDevice::erase(bd_addr_t addr, bd_size_t size)
addr += _erase_size;
size -= _erase_size;
}
#endif
return 0;
}

View File

@ -45,7 +45,8 @@
* bd.deinit();
* }
*/
class HeapBlockDevice : public BlockDevice {
class HeapBlockDevice : public BlockDevice
{
public:
/** Lifetime of the memory block device
@ -100,19 +101,19 @@ public:
*
* @return Size of a readable block in bytes
*/
virtual bd_size_t get_read_size();
virtual bd_size_t get_read_size() const;
/** Get the size of a programable block
*
* @return Size of a programable block in bytes
*/
virtual bd_size_t get_program_size();
virtual bd_size_t get_program_size() const;
/** Get the size of a eraseable block
*
* @return Size of a eraseable block in bytes
*/
virtual bd_size_t get_erase_size();
virtual bd_size_t get_erase_size() const;
/** Get the total size of the underlying device
*

View File

@ -104,17 +104,17 @@ bd_error_t SlicingBlockDevice::erase(bd_addr_t addr, bd_size_t size)
return _bd->erase(addr + _start, size);
}
bd_size_t SlicingBlockDevice::get_read_size()
bd_size_t SlicingBlockDevice::get_read_size() const
{
return _bd->get_read_size();
}
bd_size_t SlicingBlockDevice::get_program_size()
bd_size_t SlicingBlockDevice::get_program_size() const
{
return _bd->get_program_size();
}
bd_size_t SlicingBlockDevice::get_erase_size()
bd_size_t SlicingBlockDevice::get_erase_size() const
{
return _bd->get_erase_size();
}

View File

@ -45,7 +45,8 @@
* // Create a block device that maps to the middle 32 blocks
* SlicingBlockDevice slice3(&mem, 16*512, -16*512);
*/
class SlicingBlockDevice : public BlockDevice {
class SlicingBlockDevice : public BlockDevice
{
public:
/** Lifetime of the memory block device
*
@ -117,21 +118,21 @@ public:
*
* @return Size of a readable block in bytes
*/
virtual bd_size_t get_read_size();
virtual bd_size_t get_read_size() const;
/** Get the size of a programable block
*
* @return Size of a programable block in bytes
* @note Must be a multiple of the read size
*/
virtual bd_size_t get_program_size();
virtual bd_size_t get_program_size() const;
/** Get the size of a eraseable block
*
* @return Size of a eraseable block in bytes
* @note Must be a multiple of the program size
*/
virtual bd_size_t get_erase_size();
virtual bd_size_t get_erase_size() const;
/** Get the total size of the underlying device
*

View File

@ -26,11 +26,13 @@
using namespace mbed;
FATDirHandle::FATDirHandle(const FATFS_DIR &the_dir, PlatformMutex * mutex): _mutex(mutex) {
FATDirHandle::FATDirHandle(const FATFS_DIR &the_dir, PlatformMutex * mutex): _mutex(mutex)
{
dir = the_dir;
}
int FATDirHandle::closedir() {
int FATDirHandle::closedir()
{
lock();
FRESULT retval = f_closedir(&dir);
fat_filesystem_set_errno(retval);
@ -39,7 +41,8 @@ int FATDirHandle::closedir() {
return retval;
}
struct dirent *FATDirHandle::readdir() {
struct dirent *FATDirHandle::readdir()
{
FILINFO finfo;
lock();
@ -76,14 +79,16 @@ struct dirent *FATDirHandle::readdir() {
#endif /* _USE_LFN */
}
void FATDirHandle::rewinddir() {
void FATDirHandle::rewinddir()
{
lock();
dir.index = 0;
fat_filesystem_set_errno(FR_OK);
unlock();
}
off_t FATDirHandle::telldir() {
off_t FATDirHandle::telldir()
{
lock();
off_t offset = dir.index;
fat_filesystem_set_errno(FR_OK);
@ -91,18 +96,21 @@ off_t FATDirHandle::telldir() {
return offset;
}
void FATDirHandle::seekdir(off_t location) {
void FATDirHandle::seekdir(off_t location)
{
lock();
dir.index = location;
fat_filesystem_set_errno(FR_OK);
unlock();
}
void FATDirHandle::lock() {
void FATDirHandle::lock()
{
_mutex->lock();
}
void FATDirHandle::unlock() {
void FATDirHandle::unlock()
{
_mutex->unlock();
}

View File

@ -27,9 +27,10 @@
using namespace mbed;
class FATDirHandle : public DirHandle {
class FATDirHandle : public DirHandle
{
public:
public:
FATDirHandle(const FATFS_DIR &the_dir, PlatformMutex * mutex);
virtual int closedir();
virtual struct dirent *readdir();
@ -37,14 +38,14 @@ class FATDirHandle : public DirHandle {
virtual off_t telldir();
virtual void seekdir(off_t location);
protected:
protected:
virtual void lock();
virtual void unlock();
PlatformMutex * _mutex;
private:
private:
FATFS_DIR dir;
struct dirent cur_entry;

View File

@ -26,11 +26,13 @@
#include "FATFileHandle.h"
#include "FATMisc.h"
FATFileHandle::FATFileHandle(FIL fh, PlatformMutex * mutex): _mutex(mutex) {
FATFileHandle::FATFileHandle(FIL fh, PlatformMutex * mutex): _mutex(mutex)
{
_fh = fh;
}
int FATFileHandle::close() {
int FATFileHandle::close()
{
lock();
FRESULT retval = f_close(&_fh);
fat_filesystem_set_errno(retval);
@ -39,7 +41,8 @@ int FATFileHandle::close() {
return retval;
}
ssize_t FATFileHandle::write(const void* buffer, size_t length) {
ssize_t FATFileHandle::write(const void* buffer, size_t length)
{
lock();
UINT n;
FRESULT res = f_write(&_fh, buffer, length, &n);
@ -53,7 +56,8 @@ ssize_t FATFileHandle::write(const void* buffer, size_t length) {
return n;
}
ssize_t FATFileHandle::read(void* buffer, size_t length) {
ssize_t FATFileHandle::read(void* buffer, size_t length)
{
lock();
debug_if(FFS_DBG, "read(%d)\n", length);
UINT n;
@ -68,12 +72,14 @@ ssize_t FATFileHandle::read(void* buffer, size_t length) {
return n;
}
int FATFileHandle::isatty() {
int FATFileHandle::isatty()
{
fat_filesystem_set_errno(FR_OK);
return 0;
}
off_t FATFileHandle::lseek(off_t position, int whence) {
off_t FATFileHandle::lseek(off_t position, int whence)
{
lock();
if (whence == SEEK_END) {
position += _fh.fsize;
@ -93,7 +99,8 @@ off_t FATFileHandle::lseek(off_t position, int whence) {
}
}
int FATFileHandle::fsync() {
int FATFileHandle::fsync()
{
lock();
FRESULT res = f_sync(&_fh);
fat_filesystem_set_errno(res);
@ -106,7 +113,8 @@ int FATFileHandle::fsync() {
return 0;
}
off_t FATFileHandle::flen() {
off_t FATFileHandle::flen()
{
lock();
off_t size = _fh.fsize;
fat_filesystem_set_errno(FR_OK);
@ -114,10 +122,12 @@ off_t FATFileHandle::flen() {
return size;
}
void FATFileHandle::lock() {
void FATFileHandle::lock()
{
_mutex->lock();
}
void FATFileHandle::unlock() {
void FATFileHandle::unlock()
{
_mutex->unlock();
}

View File

@ -27,7 +27,8 @@
using namespace mbed;
class FATFileHandle : public FileHandle {
class FATFileHandle : public FileHandle
{
public:
FATFileHandle(FIL fh, PlatformMutex * mutex);

View File

@ -62,44 +62,50 @@ static SingletonPtr<PlatformMutex> _ffs_mutex;
// FAT driver functions
DWORD get_fattime(void) {
DWORD get_fattime(void)
{
time_t rawtime;
time(&rawtime);
struct tm *ptm = localtime(&rawtime);
return (DWORD)(ptm->tm_year - 80) << 25
| (DWORD)(ptm->tm_mon + 1 ) << 21
| (DWORD)(ptm->tm_mday ) << 16
| (DWORD)(ptm->tm_hour ) << 11
| (DWORD)(ptm->tm_min ) << 5
| (DWORD)(ptm->tm_sec/2 );
| (DWORD)(ptm->tm_mon + 1 ) << 21
| (DWORD)(ptm->tm_mday ) << 16
| (DWORD)(ptm->tm_hour ) << 11
| (DWORD)(ptm->tm_min ) << 5
| (DWORD)(ptm->tm_sec/2 );
}
// Implementation of diskio functions (see ChaN/diskio.h)
DSTATUS disk_status(BYTE pdrv) {
DSTATUS disk_status(BYTE pdrv)
{
debug_if(FFS_DBG, "disk_status on pdrv [%d]\n", pdrv);
return RES_OK;
}
DSTATUS disk_initialize(BYTE pdrv) {
DSTATUS disk_initialize(BYTE pdrv)
{
debug_if(FFS_DBG, "disk_initialize on pdrv [%d]\n", pdrv);
return (DSTATUS)_ffs[pdrv]->init();
}
DRESULT disk_read(BYTE pdrv, BYTE *buff, DWORD sector, UINT count) {
DRESULT disk_read(BYTE pdrv, BYTE *buff, DWORD sector, UINT count)
{
debug_if(FFS_DBG, "disk_read(sector %d, count %d) on pdrv [%d]\n", sector, count, pdrv);
bd_size_t ssize = _ffs[pdrv]->get_write_size();
int err = _ffs[pdrv]->read(buff, sector*ssize, count*ssize);
return err ? RES_PARERR : RES_OK;
}
DRESULT disk_write(BYTE pdrv, const BYTE *buff, DWORD sector, UINT count) {
DRESULT disk_write(BYTE pdrv, const BYTE *buff, DWORD sector, UINT count)
{
debug_if(FFS_DBG, "disk_write(sector %d, count %d) on pdrv [%d]\n", sector, count, pdrv);
bd_size_t ssize = _ffs[pdrv]->get_write_size();
int err = _ffs[pdrv]->write(buff, sector*ssize, count*ssize);
return err ? RES_PARERR : RES_OK;
}
DRESULT disk_ioctl(BYTE pdrv, BYTE cmd, void *buff) {
DRESULT disk_ioctl(BYTE pdrv, BYTE cmd, void *buff)
{
debug_if(FFS_DBG, "disk_ioctl(%d)\n", cmd);
switch (cmd) {
case CTRL_SYNC:
@ -134,18 +140,21 @@ DRESULT disk_ioctl(BYTE pdrv, BYTE cmd, void *buff) {
// Filesystem implementation (See FATFilySystem.h)
FATFileSystem::FATFileSystem(const char *n, BlockDevice *bd)
: FileSystemLike(n), _id(-1) {
: FileSystemLike(n), _id(-1)
{
if (bd) {
mount(bd);
}
}
FATFileSystem::~FATFileSystem() {
FATFileSystem::~FATFileSystem()
{
// nop if unmounted
unmount();
}
int FATFileSystem::mount(BlockDevice *bd, bool force) {
int FATFileSystem::mount(BlockDevice *bd, bool force)
{
lock();
if (_id != -1) {
unlock();
@ -170,7 +179,8 @@ int FATFileSystem::mount(BlockDevice *bd, bool force) {
return -1;
}
int FATFileSystem::unmount() {
int FATFileSystem::unmount()
{
lock();
if (_id == -1) {
unlock();
@ -185,7 +195,8 @@ int FATFileSystem::unmount() {
return res == 0 ? 0 : -1;
}
int FATFileSystem::sync() {
int FATFileSystem::sync()
{
lock();
if (_id == -1) {
unlock();
@ -200,7 +211,8 @@ int FATFileSystem::sync() {
/* See http://elm-chan.org/fsw/ff/en/mkfs.html for details of f_mkfs() and
* associated arguments. */
int FATFileSystem::format(BlockDevice *bd, int allocation_unit) {
int FATFileSystem::format(BlockDevice *bd, int allocation_unit)
{
FATFileSystem fs("");
int err = fs.mount(bd, false);
if (err) {
@ -220,7 +232,8 @@ int FATFileSystem::format(BlockDevice *bd, int allocation_unit) {
return res == 0 ? 0 : -1;
}
FileHandle *FATFileSystem::open(const char* name, int flags) {
FileHandle *FATFileSystem::open(const char* name, int flags)
{
lock();
debug_if(FFS_DBG, "open(%s) on filesystem [%s], drv [%s]\n", name, getName(), _fsid);
char n[64];
@ -259,7 +272,8 @@ FileHandle *FATFileSystem::open(const char* name, int flags) {
return handle;
}
int FATFileSystem::remove(const char *filename) {
int FATFileSystem::remove(const char *filename)
{
lock();
FRESULT res = f_unlink(filename);
fat_filesystem_set_errno(res);
@ -272,7 +286,8 @@ int FATFileSystem::remove(const char *filename) {
return 0;
}
int FATFileSystem::rename(const char *oldname, const char *newname) {
int FATFileSystem::rename(const char *oldname, const char *newname)
{
lock();
FRESULT res = f_rename(oldname, newname);
fat_filesystem_set_errno(res);
@ -285,7 +300,8 @@ int FATFileSystem::rename(const char *oldname, const char *newname) {
return 0;
}
DirHandle *FATFileSystem::opendir(const char *name) {
DirHandle *FATFileSystem::opendir(const char *name)
{
lock();
FATFS_DIR dir;
FRESULT res = f_opendir(&dir, name);
@ -299,7 +315,8 @@ DirHandle *FATFileSystem::opendir(const char *name) {
return handle;
}
int FATFileSystem::mkdir(const char *name, mode_t mode) {
int FATFileSystem::mkdir(const char *name, mode_t mode)
{
lock();
FRESULT res = f_mkdir(name);
fat_filesystem_set_errno(res);
@ -307,7 +324,8 @@ int FATFileSystem::mkdir(const char *name, mode_t mode) {
return res == 0 ? 0 : -1;
}
int FATFileSystem::stat(const char *name, struct stat *st) {
int FATFileSystem::stat(const char *name, struct stat *st)
{
lock();
FILINFO f;
memset(&f, 0, sizeof(f));
@ -319,24 +337,27 @@ int FATFileSystem::stat(const char *name, struct stat *st) {
return -1;
}
/* ARMCC doesnt support stat(), and these symbols are not defined by the toolchain. */
#ifdef TOOLCHAIN_GCC
/* ARMCC doesnt support stat(), and these symbols are not defined by the toolchain.
* Build only for GCC_ARM compiler. */
#if defined(__GNU__)
st->st_size = f.fsize;
st->st_mode = 0;
st->st_mode |= (f.fattrib & AM_DIR) ? S_IFDIR : S_IFREG;
st->st_mode |= (f.fattrib & AM_RDO) ?
(S_IRUSR | S_IXUSR | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH) :
(S_IRWXU | S_IRWXG | S_IRWXO);
#endif /* TOOLCHAIN_GCC */
(S_IRUSR | S_IXUSR | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH) :
(S_IRWXU | S_IRWXG | S_IRWXO);
#endif /* __GNU__ */
unlock();
return res == 0 ? 0 : -1;
}
void FATFileSystem::lock() {
void FATFileSystem::lock()
{
_ffs_mutex->lock();
}
void FATFileSystem::unlock() {
void FATFileSystem::unlock()
{
_ffs_mutex->unlock();
}

View File

@ -32,13 +32,14 @@
using namespace mbed;
/**
* FATFileSystem based on ChaN's Fat Filesystem library v0.8
* FATFileSystem based on ChaN's Fat Filesystem library v0.8
*/
class FATFileSystem : public FileSystemLike {
class FATFileSystem : public FileSystemLike
{
public:
FATFileSystem(const char* n, BlockDevice *bd = NULL);
virtual ~FATFileSystem();
/**
* @brief Mounts the filesystem
*
@ -49,7 +50,7 @@ public:
* Flag to underlying filesystem to force the mounting of the filesystem.
*/
virtual int mount(BlockDevice *bd, bool force = true);
/**
* Unmounts the filesystem
*/
@ -59,7 +60,7 @@ public:
* Flush any underlying transactions
*/
virtual int sync();
/**
* @brief Formats a logical drive, FDISK partitioning rule.
*
@ -81,22 +82,22 @@ public:
* Opens a file on the filesystem
*/
virtual FileHandle *open(const char* name, int flags);
/**
* Removes a file path
*/
virtual int remove(const char *filename);
/**
* Renames a file
*/
virtual int rename(const char *oldname, const char *newname);
/**
* Opens a directory on the filesystem
*/
virtual DirHandle *opendir(const char *name);
/**
* Creates a directory path
*/
@ -106,12 +107,34 @@ public:
* Store information about file in stat structure
*/
virtual int stat(const char *name, struct stat *st);
protected:
FATFS _fs; // Work area (file system object) for logical drive
char _fsid[2];
int _id;
/* Access to the underlying FAT filesystem implementation from multiple
* concurrent clients (i.e. threads) is serialised using a single
* platform mutex (_ffs_mutex) The implementation is therefore thread
* safe (but this requires further validation and testing).
* - The platform mutex _ffs_mutex is defined in the FileSystemLike
* implementation.
* - FileSystemLike uses the mutex to gain exclusive access to the
* underlying block device for mount()/unmount()/format()/sync()
* operations.
* - FileSystemLike::open() uses the mutex to serialise FATFileHandle
* object creation. The FATFileHandle constructor is passed a pointer
* to the platform mutex so file operations (e.g. read()/write()/flen()
* /fsync()) are serialised with the rest of the implementation.
* - FileSystemLike::opendir() uses the mutex to serialise FATDirHandle
* object creation. The FATDirHandle constructor is passed a pointer
* to the platform mutex so directory operations (e.g. readdir()/
* telldir()/rewinddir()/closedir()) are serialised with the rest
* of the implementation.
* - The platform mutex _ffs_mutex is taken/given using the lock()/unlock()
* methods defined below, and similar helper methods exist in the
* FATFileHandle and FATDirHandle classes.
*/
virtual void lock();
virtual void unlock();
};

View File

@ -22,12 +22,6 @@
#include "platform/retarget.h"
/* @brief Set errno based on the error code returned from underlying filesystem
*
* @param res result returned from underlying filesystem
*
* @return No return value
*/
void fat_filesystem_set_errno(FRESULT res)
{
switch(res) {

View File

@ -1,6 +1,6 @@
/*
* mbed Microcontroller Library
* Copyright (c) 2006-2016 ARM Limited
* Copyright (c) 2006-2017 ARM Limited
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -22,6 +22,15 @@
#include "ff.h"
void fat_filesystem_set_errno(FRESULT res);
/* @brief Set errno based on the error code returned from underlying FAT32 filesystem.
*
* @note Note that errno reporting is not thread safe as this is not supported
* by current versions of standard libraries.
*
* @param res result returned from underlying filesystem which is mapped to a
* suitable errno value.
*
* @return No return value
*/void fat_filesystem_set_errno(FRESULT res);
#endif /* FILESYSTEM_FAT_MISC_H */

View File

@ -11,66 +11,71 @@
namespace mbed
{
class MemFileSystem : public FATFileSystem
class MemFileSystem : public FATFileSystem
{
public:
// 2000 sectors, each 512 bytes (malloced as required)
char *sectors[2000];
MemFileSystem(const char* name) : FATFileSystem(name)
{
public:
// 2000 sectors, each 512 bytes (malloced as required)
char *sectors[2000];
MemFileSystem(const char* name) : FATFileSystem(name) {
memset(sectors, 0, sizeof(sectors));
}
virtual ~MemFileSystem() {
for(int i = 0; i < 2000; i++) {
if(sectors[i]) {
free(sectors[i]);
}
memset(sectors, 0, sizeof(sectors));
}
virtual ~MemFileSystem()
{
for(int i = 0; i < 2000; i++) {
if(sectors[i]) {
free(sectors[i]);
}
}
// read a sector in to the buffer, return 0 if ok
virtual int disk_read(char *buffer, int sector) {
if(sectors[sector] == 0) {
// nothing allocated means sector is empty
memset(buffer, 0, 512);
} else {
memcpy(buffer, sectors[sector], 512);
}
// read a sector in to the buffer, return 0 if ok
virtual int disk_read(char *buffer, int sector)
{
if(sectors[sector] == 0) {
// nothing allocated means sector is empty
memset(buffer, 0, 512);
} else {
memcpy(buffer, sectors[sector], 512);
}
return 0;
}
// write a sector from the buffer, return 0 if ok
virtual int disk_write(const char *buffer, int sector)
{
// if buffer is zero deallocate sector
char zero[512];
memset(zero, 0, 512);
if(memcmp(zero, buffer, 512)==0) {
if(sectors[sector] != 0) {
free(sectors[sector]);
sectors[sector] = 0;
}
return 0;
}
// write a sector from the buffer, return 0 if ok
virtual int disk_write(const char *buffer, int sector) {
// if buffer is zero deallocate sector
char zero[512];
memset(zero, 0, 512);
if(memcmp(zero, buffer, 512)==0) {
if(sectors[sector] != 0) {
free(sectors[sector]);
sectors[sector] = 0;
}
return 0;
// else allocate a sector if needed, and write
if(sectors[sector] == 0) {
char *sec = (char*)malloc(512);
if(sec==0) {
return 1; // out of memory
}
// else allocate a sector if needed, and write
if(sectors[sector] == 0) {
char *sec = (char*)malloc(512);
if(sec==0) {
return 1; // out of memory
}
sectors[sector] = sec;
}
memcpy(sectors[sector], buffer, 512);
return 0;
sectors[sector] = sec;
}
// return the number of sectors
virtual int disk_sectors() {
return sizeof(sectors)/sizeof(sectors[0]);
}
};
memcpy(sectors[sector], buffer, 512);
return 0;
}
// return the number of sectors
virtual int disk_sectors()
{
return sizeof(sectors)/sizeof(sectors[0]);
}
};
}

View File

@ -422,7 +422,6 @@ extern "C" int _fstat(int fd, struct stat *st) {
st->st_mode = S_IFCHR;
return 0;
}
/* todo: 20170120 this should now be made to work as _stat() is implemented */
errno = EBADF;
return -1;
}

View File

@ -14,19 +14,19 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*
* This file contains symbols used by the implementation that are not present
* in the armcc errno.h, or sys/stat.h. These are used in for the POSIX
* filesystem API to return errno codes, for example.
*/
#ifndef RETARGET_H
#define RETARGET_H
#if defined TOOLCHAIN_ARM_STD || defined TOOLCHAIN_IAR
/* The following are errno.h definitions not currently present in the ARMCC
* errno.h. Note, ARMCC errno.h defines some symbols values differing from
* GCC_ARM/IAR/standard POSIX definitions.Guard against this and future
* changes by changing the symbol definition for filesystem use. */
#if defined(__ARMCC_VERSION) || defined(__ICCARM__)
/* The intent of this section is to unify the errno error values to match
* the POSIX definitions for the GCC_ARM, ARMCC and IAR compilers. This is
* necessary because the ARMCC/IAR errno.h, or sys/stat.h are missing some
* symbol definitions used by the POSIX filesystem API to return errno codes.
* Note also that ARMCC errno.h defines some symbol values differently from
* the GCC_ARM/IAR/standard POSIX definitions. The definitions guard against
* this and future changes by changing the symbol definition as shown below. */
#ifdef ENOENT
#undef ENOENT
#endif
@ -106,6 +106,6 @@
#define S_IWOTH 0000002 /* write permission, other */
#define S_IXOTH 0000001/* execute/search permission, other */
#endif /* TOOLCHAIN_ARM_STD || defined TOOLCHAIN_IAR */
#endif /* defined(__ARMCC_VERSION) || defined(__ICCARM__) */
#endif /* RETARGET_H */

View File

@ -24,9 +24,7 @@ from tools.settings import ROOT, BUILD_DIR
BUILD_DIR = getenv("MBED_BUILD_DIR") or BUILD_DIR
# Embedded Libraries Sources
FEATURES_DIR = join(ROOT, "features")
LIB_DIR = join(FEATURES_DIR, "unsupported")
LIB_DIR = join(ROOT, "features/unsupported")
TOOLS = join(ROOT, "tools")
TOOLS_DATA = join(TOOLS, "data")
@ -78,12 +76,6 @@ ETH_LIBRARY = join(NET_LIBRARIES, "eth")
VODAFONE_LIBRARY = join(NET_LIBRARIES, "VodafoneUSBModem")
UBLOX_LIBRARY = join(NET_LIBRARIES, "UbloxUSBModem")
# FS
FS_PATH = join(FEATURES_DIR, "filesystem")
FAT_FS = join(FS_PATH, "fat")
SD_FS = join(FS_PATH, "sd")
FS_LIBRARY = join(BUILD_DIR, "fat")
# DSP
DSP = join(LIB_DIR, "dsp")
DSP_CMSIS = join(DSP, "cmsis_dsp")

View File

@ -216,13 +216,6 @@ TESTS = [
"supported": DEFAULT_SUPPORT,
"automated": True,
},
{
"id": "MBED_A12", "description": "SD File System",
"source_dir": join(TEST_DIR, "mbed", "sd"),
"dependencies": [MBED_LIBRARIES, TEST_MBED_LIB, FS_LIBRARY],
"automated": True,
"peripherals": ["SD"]
},
{
"id": "MBED_A13", "description": "I2C MMA7660 accelerometer",
"source_dir": join(TEST_DIR, "mbed", "i2c_MMA7660"),
@ -394,29 +387,6 @@ TESTS = [
"dependencies": [MBED_LIBRARIES]
},
# performance related tests
{
"id": "PERF_1", "description": "SD Stdio R/W Speed",
"source_dir": join(TEST_DIR, "mbed", "sd_perf_stdio"),
"dependencies": [MBED_LIBRARIES, TEST_MBED_LIB, FS_LIBRARY],
"automated": True,
"peripherals": ["SD"]
},
{
"id": "PERF_2", "description": "SD FileHandle R/W Speed",
"source_dir": join(TEST_DIR, "mbed", "sd_perf_fhandle"),
"dependencies": [MBED_LIBRARIES, TEST_MBED_LIB, FS_LIBRARY],
"automated": True,
"peripherals": ["SD"]
},
{
"id": "PERF_3", "description": "SD FatFS R/W Speed",
"source_dir": join(TEST_DIR, "mbed", "sd_perf_fatfs"),
"dependencies": [MBED_LIBRARIES, TEST_MBED_LIB, FS_LIBRARY],
"automated": True,
"peripherals": ["SD"]
},
# Not automated MBED tests
{
@ -538,12 +508,6 @@ TESTS = [
"source_dir": join(TEST_DIR, "mbed", "dir"),
"dependencies": [MBED_LIBRARIES],
},
{
"id": "MBED_19", "description": "SD FS Directory",
"source_dir": join(TEST_DIR, "mbed", "dir_sd"),
"dependencies": [MBED_LIBRARIES, FS_LIBRARY],
"peripherals": ["SD"]
},
{
"id": "MBED_20", "description": "InterruptIn 2",
"source_dir": join(TEST_DIR, "mbed", "interruptin_2"),
@ -853,7 +817,7 @@ TESTS = [
{
"id": "RTOS_9", "description": "SD File write-read",
"source_dir": join(TEST_DIR, "rtos", "mbed", "file"),
"dependencies": [MBED_LIBRARIES, RTOS_LIBRARIES, TEST_MBED_LIB, FS_LIBRARY],
"dependencies": [MBED_LIBRARIES, RTOS_LIBRARIES, TEST_MBED_LIB],
"automated": True,
"peripherals": ["SD"],
"mcu": ["LPC1768", "LPC11U24", "LPC812", "KL25Z", "HEXIWEAR",
@ -1092,7 +1056,7 @@ TESTS = [
{
"id": "EXAMPLE_2", "description": "FS + RTOS",
"source_dir": join(TEST_DIR, "mbed", "fs"),
"dependencies": [MBED_LIBRARIES, RTOS_LIBRARIES, TEST_MBED_LIB, FS_LIBRARY],
"dependencies": [MBED_LIBRARIES, RTOS_LIBRARIES, TEST_MBED_LIB],
},
# CPPUTEST Library provides Unit testing Framework