Skip to content

Commit c0c501c

Browse files
authored
Merge pull request #5768 from deepikabhavnani/storage_stats
Added statvfs API to get storage statistics
2 parents 2c5fedc + d5cf4a6 commit c0c501c

File tree

10 files changed

+188
-33
lines changed

10 files changed

+188
-33
lines changed

features/filesystem/FileSystem.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,11 @@ int FileSystem::mkdir(const char *path, mode_t mode)
5151
return -ENOSYS;
5252
}
5353

54+
int FileSystem::statvfs(const char *path, struct statvfs *buf)
55+
{
56+
return -ENOSYS;
57+
}
58+
5459
int FileSystem::file_sync(fs_file_t file)
5560
{
5661
return 0;

features/filesystem/FileSystem.h

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,14 @@ class FileSystem : public FileSystemLike {
109109
*/
110110
virtual int mkdir(const char *path, mode_t mode);
111111

112+
/** Store information about the mounted filesystem in a statvfs structure
113+
*
114+
* @param path The name of the file to find information about
115+
* @param buf The stat buffer to write to
116+
* @return 0 on success, negative error code on failure
117+
*/
118+
virtual int statvfs(const char *path, struct statvfs *buf);
119+
112120
protected:
113121
friend class File;
114122
friend class Dir;
@@ -143,7 +151,7 @@ class FileSystem : public FileSystemLike {
143151
*
144152
* @param file File handle
145153
* @param buffer The buffer to write from
146-
* @param size The number of bytes to write
154+
* @param size The number of bytes to write
147155
* @return The number of bytes written, negative error on failure
148156
*/
149157
virtual ssize_t file_write(fs_file_t file, const void *buffer, size_t size) = 0;
@@ -240,7 +248,7 @@ class FileSystem : public FileSystemLike {
240248
*/
241249
virtual void dir_rewind(fs_dir_t dir);
242250

243-
/** Get the sizeof the directory
251+
/** Get the sizeof the directory
244252
*
245253
* @param dir Dir handle
246254
* @return Number of files in the directory

features/filesystem/fat/FATFileSystem.cpp

Lines changed: 77 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -275,12 +275,14 @@ FATFileSystem::~FATFileSystem()
275275
unmount();
276276
}
277277

278-
int FATFileSystem::mount(BlockDevice *bd) {
278+
int FATFileSystem::mount(BlockDevice *bd)
279+
{
279280
// requires duplicate definition to allow virtual overload to work
280281
return mount(bd, true);
281282
}
282283

283-
int FATFileSystem::mount(BlockDevice *bd, bool mount) {
284+
int FATFileSystem::mount(BlockDevice *bd, bool mount)
285+
{
284286
lock();
285287
if (_id != -1) {
286288
unlock();
@@ -322,7 +324,8 @@ int FATFileSystem::unmount()
322324

323325
/* See http://elm-chan.org/fsw/ff/en/mkfs.html for details of f_mkfs() and
324326
* associated arguments. */
325-
int FATFileSystem::format(BlockDevice *bd, bd_size_t cluster_size) {
327+
int FATFileSystem::format(BlockDevice *bd, bd_size_t cluster_size)
328+
{
326329
FATFileSystem fs;
327330
int err = fs.mount(bd, false);
328331
if (err) {
@@ -345,7 +348,8 @@ int FATFileSystem::format(BlockDevice *bd, bd_size_t cluster_size) {
345348
return 0;
346349
}
347350

348-
int FATFileSystem::reformat(BlockDevice *bd, int allocation_unit) {
351+
int FATFileSystem::reformat(BlockDevice *bd, int allocation_unit)
352+
{
349353
lock();
350354
if (_id != -1) {
351355
if (!bd) {
@@ -375,7 +379,8 @@ int FATFileSystem::reformat(BlockDevice *bd, int allocation_unit) {
375379
return err;
376380
}
377381

378-
int FATFileSystem::remove(const char *path) {
382+
int FATFileSystem::remove(const char *path)
383+
{
379384
Deferred<const char*> fpath = fat_path_prefix(_id, path);
380385

381386
lock();
@@ -388,7 +393,8 @@ int FATFileSystem::remove(const char *path) {
388393
return fat_error_remap(res);
389394
}
390395

391-
int FATFileSystem::rename(const char *oldpath, const char *newpath) {
396+
int FATFileSystem::rename(const char *oldpath, const char *newpath)
397+
{
392398
Deferred<const char*> oldfpath = fat_path_prefix(_id, oldpath);
393399
Deferred<const char*> newfpath = fat_path_prefix(_id, newpath);
394400

@@ -402,7 +408,8 @@ int FATFileSystem::rename(const char *oldpath, const char *newpath) {
402408
return fat_error_remap(res);
403409
}
404410

405-
int FATFileSystem::mkdir(const char *path, mode_t mode) {
411+
int FATFileSystem::mkdir(const char *path, mode_t mode)
412+
{
406413
Deferred<const char*> fpath = fat_path_prefix(_id, path);
407414

408415
lock();
@@ -415,7 +422,8 @@ int FATFileSystem::mkdir(const char *path, mode_t mode) {
415422
return fat_error_remap(res);
416423
}
417424

418-
int FATFileSystem::stat(const char *path, struct stat *st) {
425+
int FATFileSystem::stat(const char *path, struct stat *st)
426+
{
419427
Deferred<const char*> fpath = fat_path_prefix(_id, path);
420428

421429
lock();
@@ -442,17 +450,49 @@ int FATFileSystem::stat(const char *path, struct stat *st) {
442450
return 0;
443451
}
444452

445-
void FATFileSystem::lock() {
453+
int FATFileSystem::statvfs(const char *path, struct statvfs *buf)
454+
{
455+
456+
memset(buf, 0, sizeof(struct statvfs));
457+
FATFS *fs;
458+
DWORD fre_clust;
459+
460+
lock();
461+
FRESULT res = f_getfree(_fsid, &fre_clust, &fs);
462+
if (res != FR_OK) {
463+
unlock();
464+
return fat_error_remap(res);
465+
}
466+
467+
buf->f_bsize = fs->ssize;
468+
buf->f_frsize = fs->ssize;
469+
buf->f_blocks = (fs->n_fatent - 2) * fs->csize;
470+
buf->f_bfree = fre_clust * fs->csize;
471+
buf->f_bavail = buf->f_bfree;
472+
#if FF_USE_LFN
473+
buf->f_namemax = FF_LFN_BUF;
474+
#else
475+
buf->f_namemax = FF_SFN_BUF;
476+
#endif
477+
478+
unlock();
479+
return 0;
480+
}
481+
482+
void FATFileSystem::lock()
483+
{
446484
_ffs_mutex->lock();
447485
}
448486

449-
void FATFileSystem::unlock() {
487+
void FATFileSystem::unlock()
488+
{
450489
_ffs_mutex->unlock();
451490
}
452491

453492

454493
////// File operations //////
455-
int FATFileSystem::file_open(fs_file_t *file, const char *path, int flags) {
494+
int FATFileSystem::file_open(fs_file_t *file, const char *path, int flags)
495+
{
456496
debug_if(FFS_DBG, "open(%s) on filesystem [%s], drv [%s]\n", path, getName(), _id);
457497

458498
FIL *fh = new FIL;
@@ -496,7 +536,8 @@ int FATFileSystem::file_open(fs_file_t *file, const char *path, int flags) {
496536
return 0;
497537
}
498538

499-
int FATFileSystem::file_close(fs_file_t file) {
539+
int FATFileSystem::file_close(fs_file_t file)
540+
{
500541
FIL *fh = static_cast<FIL*>(file);
501542

502543
lock();
@@ -507,7 +548,8 @@ int FATFileSystem::file_close(fs_file_t file) {
507548
return fat_error_remap(res);
508549
}
509550

510-
ssize_t FATFileSystem::file_read(fs_file_t file, void *buffer, size_t len) {
551+
ssize_t FATFileSystem::file_read(fs_file_t file, void *buffer, size_t len)
552+
{
511553
FIL *fh = static_cast<FIL*>(file);
512554

513555
lock();
@@ -523,7 +565,8 @@ ssize_t FATFileSystem::file_read(fs_file_t file, void *buffer, size_t len) {
523565
}
524566
}
525567

526-
ssize_t FATFileSystem::file_write(fs_file_t file, const void *buffer, size_t len) {
568+
ssize_t FATFileSystem::file_write(fs_file_t file, const void *buffer, size_t len)
569+
{
527570
FIL *fh = static_cast<FIL*>(file);
528571

529572
lock();
@@ -539,7 +582,8 @@ ssize_t FATFileSystem::file_write(fs_file_t file, const void *buffer, size_t len
539582
}
540583
}
541584

542-
int FATFileSystem::file_sync(fs_file_t file) {
585+
int FATFileSystem::file_sync(fs_file_t file)
586+
{
543587
FIL *fh = static_cast<FIL*>(file);
544588

545589
lock();
@@ -552,7 +596,8 @@ int FATFileSystem::file_sync(fs_file_t file) {
552596
return fat_error_remap(res);
553597
}
554598

555-
off_t FATFileSystem::file_seek(fs_file_t file, off_t offset, int whence) {
599+
off_t FATFileSystem::file_seek(fs_file_t file, off_t offset, int whence)
600+
{
556601
FIL *fh = static_cast<FIL*>(file);
557602

558603
lock();
@@ -574,7 +619,8 @@ off_t FATFileSystem::file_seek(fs_file_t file, off_t offset, int whence) {
574619
}
575620
}
576621

577-
off_t FATFileSystem::file_tell(fs_file_t file) {
622+
off_t FATFileSystem::file_tell(fs_file_t file)
623+
{
578624
FIL *fh = static_cast<FIL*>(file);
579625

580626
lock();
@@ -584,7 +630,8 @@ off_t FATFileSystem::file_tell(fs_file_t file) {
584630
return res;
585631
}
586632

587-
off_t FATFileSystem::file_size(fs_file_t file) {
633+
off_t FATFileSystem::file_size(fs_file_t file)
634+
{
588635
FIL *fh = static_cast<FIL*>(file);
589636

590637
lock();
@@ -596,7 +643,8 @@ off_t FATFileSystem::file_size(fs_file_t file) {
596643

597644

598645
////// Dir operations //////
599-
int FATFileSystem::dir_open(fs_dir_t *dir, const char *path) {
646+
int FATFileSystem::dir_open(fs_dir_t *dir, const char *path)
647+
{
600648
FATFS_DIR *dh = new FATFS_DIR;
601649
Deferred<const char*> fpath = fat_path_prefix(_id, path);
602650

@@ -614,7 +662,8 @@ int FATFileSystem::dir_open(fs_dir_t *dir, const char *path) {
614662
return 0;
615663
}
616664

617-
int FATFileSystem::dir_close(fs_dir_t dir) {
665+
int FATFileSystem::dir_close(fs_dir_t dir)
666+
{
618667
FATFS_DIR *dh = static_cast<FATFS_DIR*>(dir);
619668

620669
lock();
@@ -625,7 +674,8 @@ int FATFileSystem::dir_close(fs_dir_t dir) {
625674
return fat_error_remap(res);
626675
}
627676

628-
ssize_t FATFileSystem::dir_read(fs_dir_t dir, struct dirent *ent) {
677+
ssize_t FATFileSystem::dir_read(fs_dir_t dir, struct dirent *ent)
678+
{
629679
FATFS_DIR *dh = static_cast<FATFS_DIR*>(dir);
630680
FILINFO finfo;
631681

@@ -653,7 +703,8 @@ ssize_t FATFileSystem::dir_read(fs_dir_t dir, struct dirent *ent) {
653703
return 1;
654704
}
655705

656-
void FATFileSystem::dir_seek(fs_dir_t dir, off_t offset) {
706+
void FATFileSystem::dir_seek(fs_dir_t dir, off_t offset)
707+
{
657708
FATFS_DIR *dh = static_cast<FATFS_DIR*>(dir);
658709

659710
lock();
@@ -675,7 +726,8 @@ void FATFileSystem::dir_seek(fs_dir_t dir, off_t offset) {
675726
unlock();
676727
}
677728

678-
off_t FATFileSystem::dir_tell(fs_dir_t dir) {
729+
off_t FATFileSystem::dir_tell(fs_dir_t dir)
730+
{
679731
FATFS_DIR *dh = static_cast<FATFS_DIR*>(dir);
680732

681733
lock();
@@ -685,7 +737,8 @@ off_t FATFileSystem::dir_tell(fs_dir_t dir) {
685737
return offset;
686738
}
687739

688-
void FATFileSystem::dir_rewind(fs_dir_t dir) {
740+
void FATFileSystem::dir_rewind(fs_dir_t dir)
741+
{
689742
FATFS_DIR *dh = static_cast<FATFS_DIR*>(dir);
690743

691744
lock();

features/filesystem/fat/FATFileSystem.h

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@ class FATFileSystem : public FileSystem {
4343
*/
4444
FATFileSystem(const char *name = NULL, BlockDevice *bd = NULL);
4545
virtual ~FATFileSystem();
46-
46+
4747
/** Formats a logical drive, FDISK partitioning rule.
4848
*
4949
* The block device to format should be mounted when this function is called.
@@ -57,7 +57,7 @@ class FATFileSystem : public FileSystem {
5757
* cluster_size must be a multiple of the underlying device's allocation unit
5858
* and is currently limited to a max of 32,768 bytes. If zero, a cluster size
5959
* will be determined from the device's allocation unit. Defaults to zero.
60-
*
60+
*
6161
* @return 0 on success, negative error code on failure
6262
*/
6363
static int format(BlockDevice *bd, bd_size_t cluster_size = 0);
@@ -139,6 +139,14 @@ class FATFileSystem : public FileSystem {
139139
*/
140140
virtual int mkdir(const char *path, mode_t mode);
141141

142+
/** Store information about the mounted filesystem in a statvfs structure
143+
*
144+
* @param path The name of the file to find information about
145+
* @param buf The stat buffer to write to
146+
* @return 0 on success, negative error code on failure
147+
*/
148+
virtual int statvfs(const char *path, struct statvfs *buf);
149+
142150
protected:
143151
/** Open a file on the filesystem
144152
*
@@ -170,7 +178,7 @@ class FATFileSystem : public FileSystem {
170178
*
171179
* @param file File handle
172180
* @param buffer The buffer to write from
173-
* @param len The number of bytes to write
181+
* @param len The number of bytes to write
174182
* @return The number of bytes written, negative error on failure
175183
*/
176184
virtual ssize_t file_write(fs_file_t file, const void *buffer, size_t len);
@@ -251,7 +259,7 @@ class FATFileSystem : public FileSystem {
251259
* @param dir Dir handle
252260
*/
253261
virtual void dir_rewind(fs_dir_t dir);
254-
262+
255263
private:
256264
FATFS _fs; // Work area (file system object) for logical drive
257265
char _fsid[sizeof("0:")];

features/filesystem/littlefs/LittleFileSystem.cpp

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -336,6 +336,34 @@ int LittleFileSystem::stat(const char *name, struct stat *st)
336336
return lfs_toerror(err);
337337
}
338338

339+
static int lfs_statvfs_count(void *p, lfs_block_t b)
340+
{
341+
*(lfs_size_t *)p += 1;
342+
return 0;
343+
}
344+
345+
int LittleFileSystem::statvfs(const char *name, struct statvfs *st)
346+
{
347+
memset(st, 0, sizeof(struct statvfs));
348+
349+
lfs_size_t in_use = 0;
350+
_mutex.lock();
351+
LFS_INFO("statvfs(\"%s\", %p)", name, st);
352+
int err = lfs_traverse(&_lfs, lfs_statvfs_count, &in_use);
353+
LFS_INFO("statvfs -> %d", lfs_toerror(err));
354+
_mutex.unlock();
355+
if (err) {
356+
return err;
357+
}
358+
359+
st->f_bsize = _config.block_size;
360+
st->f_frsize = _config.block_size;
361+
st->f_blocks = _config.block_count;
362+
st->f_bfree = _config.block_count - in_use;
363+
st->f_bavail = _config.block_count - in_use;
364+
st->f_namemax = LFS_NAME_MAX;
365+
return 0;
366+
}
339367

340368
////// File operations //////
341369
int LittleFileSystem::file_open(fs_file_t *file, const char *path, int flags)

0 commit comments

Comments
 (0)